<!DOCTYPE html>


<html theme="dark" showBanner="true" hasBanner="false" > 
<link href="/blog/fontawesome/css/fontawesome.css" rel="stylesheet">
<link href="/blog/fontawesome/css/brands.css" rel="stylesheet">
<link href="/blog/fontawesome/css/solid.css" rel="stylesheet">
<script src="/blog/js/color.global.min.js" ></script>
<script src="/blog/js/load-settings.js" ></script>
<head>
  <meta charset="utf-8">
  
  
  

  
  <title>Hexo</title>
  <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">

  <link rel="preload" href="/blog/css/fonts/Roboto-Regular.ttf" as="font" type="font/ttf" crossorigin="anonymous">
  <link rel="preload" href="/blog/css/fonts/Roboto-Bold.ttf" as="font" type="font/ttf" crossorigin="anonymous">

  <meta name="description" content="一、plane数据结构1.1 struct drm_planelinux内核使用struct drm_plane表示一个plane，它们从一个drm_framebuffer接收输入数据，并将其传递给一个drm_crtc。plane控制颜色转换，并且还参与输入像素的颜色转换。定义include&#x2F;drm&#x2F;drm_plane.h； 12345678910111213141516171">
<meta property="og:type" content="article">
<meta property="og:title" content="Hexo">
<meta property="og:url" content="https://zyly2033.gitee.io/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%20plane/index.html">
<meta property="og:site_name" content="Hexo">
<meta property="og:description" content="一、plane数据结构1.1 struct drm_planelinux内核使用struct drm_plane表示一个plane，它们从一个drm_framebuffer接收输入数据，并将其传递给一个drm_crtc。plane控制颜色转换，并且还参与输入像素的颜色转换。定义include&#x2F;drm&#x2F;drm_plane.h； 12345678910111213141516171">
<meta property="og:locale" content="en_US">
<meta property="article:published_time" content="2023-09-11T12:23:16.222Z">
<meta property="article:modified_time" content="2023-09-03T14:38:25.534Z">
<meta property="article:author" content="John Doe">
<meta name="twitter:card" content="summary">
  
    <link rel="alternate" href="/blog/atom.xml" title="Hexo" type="application/atom+xml">
  
  
    <link rel="icon" media="(prefers-color-scheme: light)" href="/blog/images/favicon-light-32.png" sizes="32x32">
    <link rel="icon" media="(prefers-color-scheme: light)" href="/blog/images/favicon-light-128.png" sizes="128x128">
    <link rel="icon" media="(prefers-color-scheme: light)" href="/blog/images/favicon-light-180.png" sizes="180x180">
    <link rel="icon" media="(prefers-color-scheme: light)" href="/blog/images/favicon-light-192.png" sizes="192x192">
    <link rel="icon" media="(prefers-color-scheme: dark)" href="/blog/images/favicon-dark-32.png" sizes="32x32">
    <link rel="icon" media="(prefers-color-scheme: dark)" href="/blog/images/favicon-dark-128.png" sizes="128x128">
    <link rel="icon" media="(prefers-color-scheme: dark)" href="/blog/images/favicon-dark-180.png" sizes="180x180">
    <link rel="icon" media="(prefers-color-scheme: dark)" href="/blog/images/favicon-dark-192.png" sizes="192x192">
  
  
<link rel="stylesheet" href="/blog/css/style.css">

<meta name="generator" content="Hexo 6.3.0"></head>

<body>
  
   
  <div id="main-grid" class="shadow   ">
    <div id="nav" class=""  >
      <navbar id="navbar">
  <nav id="title-nav">
    <a href="/blog/">
      <div id="vivia-logo">
        <div class="dot"></div>
        <div class="dot"></div>
        <div class="dot"></div>
        <div class="dot"></div>
      </div>
      <div>Hexo </div>
    </a>
  </nav>
  <nav id="main-nav">
    
      <a class="main-nav-link" href="/blog/">Home</a>
    
      <a class="main-nav-link" href="/blog/archives">Archives</a>
    
      <a class="main-nav-link" href="/blog/about">About</a>
    
  </nav>
  <nav id="sub-nav">
    <a id="theme-btn" class="nav-icon">
      <span class="light-mode-icon"><svg xmlns="http://www.w3.org/2000/svg" height="20" viewBox="0 -960 960 960" width="20"><path d="M438.5-829.913v-48q0-17.452 11.963-29.476 11.964-12.024 29.326-12.024 17.363 0 29.537 12.024t12.174 29.476v48q0 17.452-11.963 29.476-11.964 12.024-29.326 12.024-17.363 0-29.537-12.024T438.5-829.913Zm0 747.826v-48q0-17.452 11.963-29.476 11.964-12.024 29.326-12.024 17.363 0 29.537 12.024t12.174 29.476v48q0 17.452-11.963 29.476-11.964 12.024-29.326 12.024-17.363 0-29.537-12.024T438.5-82.087ZM877.913-438.5h-48q-17.452 0-29.476-11.963-12.024-11.964-12.024-29.326 0-17.363 12.024-29.537t29.476-12.174h48q17.452 0 29.476 11.963 12.024 11.964 12.024 29.326 0 17.363-12.024 29.537T877.913-438.5Zm-747.826 0h-48q-17.452 0-29.476-11.963-12.024-11.964-12.024-29.326 0-17.363 12.024-29.537T82.087-521.5h48q17.452 0 29.476 11.963 12.024 11.964 12.024 29.326 0 17.363-12.024 29.537T130.087-438.5Zm660.174-290.87-34.239 32q-12.913 12.674-29.565 12.174-16.653-.5-29.327-13.174-12.674-12.673-12.554-28.826.12-16.152 12.794-28.826l33-35q12.913-12.674 30.454-12.674t30.163 12.847q12.709 12.846 12.328 30.826-.38 17.98-13.054 30.653ZM262.63-203.978l-32 34q-12.913 12.674-30.454 12.674t-30.163-12.847q-12.709-12.846-12.328-30.826.38-17.98 13.054-30.653l33.239-31q12.913-12.674 29.565-12.174 16.653.5 29.327 13.174 12.674 12.673 12.554 28.826-.12 16.152-12.794 28.826Zm466.74 33.239-32-33.239q-12.674-12.913-12.174-29.565.5-16.653 13.174-29.327 12.673-12.674 28.826-13.054 16.152-.38 28.826 12.294l35 33q12.674 12.913 12.674 30.454t-12.847 30.163q-12.846 12.709-30.826 12.328-17.98-.38-30.653-13.054ZM203.978-697.37l-34-33q-12.674-12.913-13.174-29.945-.5-17.033 12.174-29.707t31.326-13.293q18.653-.62 31.326 13.054l32 34.239q11.674 12.913 11.174 29.565-.5 16.653-13.174 29.327-12.673 12.674-28.826 12.554-16.152-.12-28.826-12.794ZM480-240q-100 0-170-70t-70-170q0-100 70-170t170-70q100 0 170 70t70 170q0 100-70 170t-170 70Zm-.247-82q65.703 0 111.475-46.272Q637-414.544 637-480.247t-45.525-111.228Q545.95-637 480.247-637t-111.475 45.525Q323-545.95 323-480.247t45.525 111.975Q414.05-322 479.753-322ZM481-481Z"/></svg></span>
      <span class="dark-mode-icon"><svg xmlns="http://www.w3.org/2000/svg" height="20" viewBox="0 -960 960 960" width="20"><path d="M480.239-116.413q-152.63 0-258.228-105.478Q116.413-327.37 116.413-480q0-130.935 77.739-227.435t206.304-125.043q43.022-9.631 63.87 10.869t3.478 62.805q-8.891 22.043-14.315 44.463-5.424 22.42-5.424 46.689 0 91.694 64.326 155.879 64.325 64.186 156.218 64.186 24.369 0 46.978-4.946 22.609-4.945 44.413-14.076 42.826-17.369 62.967 1.142 20.142 18.511 10.511 61.054Q807.174-280 712.63-198.206q-94.543 81.793-232.391 81.793Zm0-95q79.783 0 143.337-40.217 63.554-40.218 95.793-108.283-15.608 4.044-31.097 5.326-15.49 1.283-31.859.805-123.706-4.066-210.777-90.539-87.071-86.473-91.614-212.092-.24-16.369.923-31.978 1.164-15.609 5.446-30.978-67.826 32.478-108.282 96.152Q211.652-559.543 211.652-480q0 111.929 78.329 190.258 78.329 78.329 190.258 78.329ZM466.13-465.891Z"/></svg></span>
    </a>
    
      <a id="nav-rss-link" class="nav-icon mobile-hide" href="/blog/atom.xml" title="RSS Feed">
        <svg xmlns="http://www.w3.org/2000/svg" height="20" viewBox="0 -960 960 960" width="20"><path d="M198-120q-25.846 0-44.23-18.384-18.384-18.385-18.384-44.23 0-25.846 18.384-44.23 18.384-18.385 44.23-18.385 25.846 0 44.23 18.385 18.384 18.384 18.384 44.23 0 25.845-18.384 44.23Q223.846-120 198-120Zm538.385 0q-18.846 0-32.923-13.769-14.076-13.769-15.922-33.23-8.692-100.616-51.077-188.654-42.385-88.039-109.885-155.539-67.5-67.501-155.539-109.885Q283-663.462 182.385-672.154q-19.461-1.846-33.23-16.23-13.769-14.385-13.769-33.846t14.076-32.922q14.077-13.461 32.923-12.23 120.076 8.692 226.038 58.768 105.961 50.077 185.73 129.846 79.769 79.769 129.846 185.731 50.077 105.961 58.769 226.038 1.231 18.846-12.538 32.922Q756.461-120 736.385-120Zm-252 0q-18.231 0-32.423-13.461t-18.653-33.538Q418.155-264.23 348.886-333.5q-69.27-69.27-166.501-84.423-20.077-4.462-33.538-18.961-13.461-14.5-13.461-33.346 0-19.076 13.884-33.23 13.884-14.153 33.115-10.922 136.769 15.384 234.384 112.999 97.615 97.615 112.999 234.384 3.231 19.23-10.538 33.115Q505.461-120 484.385-120Z"/></svg>
      </a>
    
    <div id="nav-menu-btn" class="nav-icon">
      <svg xmlns="http://www.w3.org/2000/svg" height="20" viewBox="0 -960 960 960" width="20"><path d="M177.37-252.282q-17.453 0-29.477-11.964-12.024-11.963-12.024-29.326t12.024-29.537q12.024-12.174 29.477-12.174h605.26q17.453 0 29.477 11.964 12.024 11.963 12.024 29.326t-12.024 29.537q-12.024 12.174-29.477 12.174H177.37Zm0-186.218q-17.453 0-29.477-11.963-12.024-11.964-12.024-29.326 0-17.363 12.024-29.537T177.37-521.5h605.26q17.453 0 29.477 11.963 12.024 11.964 12.024 29.326 0 17.363-12.024 29.537T782.63-438.5H177.37Zm0-186.217q-17.453 0-29.477-11.964-12.024-11.963-12.024-29.326t12.024-29.537q12.024-12.174 29.477-12.174h605.26q17.453 0 29.477 11.964 12.024 11.963 12.024 29.326t-12.024 29.537q-12.024 12.174-29.477 12.174H177.37Z"/></svg>
    </div>
  </nav>
</navbar>
<div id="nav-dropdown" class="hidden">
  <div id="dropdown-link-list">
    
      <a class="nav-dropdown-link" href="/blog/">Home</a>
    
      <a class="nav-dropdown-link" href="/blog/archives">Archives</a>
    
      <a class="nav-dropdown-link" href="/blog/about">About</a>
    
    
      <a class="nav-dropdown-link" href="/blog/atom.xml" title="RSS Feed">RSS</a>
     
    </div>
</div>
<script>
  let dropdownBtn = document.getElementById("nav-menu-btn");
  let dropdownEle = document.getElementById("nav-dropdown");
  dropdownBtn.onclick = function() {
    dropdownEle.classList.toggle("hidden");
  }
</script>
    </div>
    <div id="sidebar-wrapper">
      <sidebar id="sidebar">
  
    <div class="widget-wrap">
  <div class="info-card">
    <div class="avatar">
      
      <div class="img-dim"></div>
    </div>
    <div class="info">
      <div class="username">Your Name </div>
      <div class="dot"></div>
      <div class="subtitle">This is the subtitle </div>
      <div class="link-list">
        
          <a class="link-btn" target="_blank" rel="noopener" href="https://twitter.com" title="Twitter"><i class="fa-brands fa-twitter"></i></a>
        
          <a class="link-btn" target="_blank" rel="noopener" href="https://store.steampowered.com" title="Steam"><i class="fa-brands fa-steam"></i></a>
        
          <a class="link-btn" target="_blank" rel="noopener" href="https://github.com" title="GitHub"><i class="fa-brands fa-github"></i></a>
         
      </div>  
    </div>
  </div>
</div>

  
  <div class="sticky">
    
      



    
      

    
      
  <div class="widget-wrap">
    <div class="widget">
      <h3 class="widget-title">Archives</h3>
      
      
        <a class="archive-link" href="/blog/archives/2023/09 ">
          September 2023 
          <div class="archive-count">8 </div>
        </a>
      
    </div>
  </div>


    
      
  <div class="widget-wrap">
    <div class="widget">
      <h3 class="widget-title">Recent Posts</h3>
      <ul>
        
          <a class="recent-link" href="/blog/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%E9%A9%B1%E5%8A%A8%E7%A8%8B%E5%BA%8F/" title="" >
            <div class="recent-link-text">
              (no title)
            </div>
          </a>
        
          <a class="recent-link" href="/blog/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%E5%AD%90%E7%B3%BB%E7%BB%9F/" title="" >
            <div class="recent-link-text">
              (no title)
            </div>
          </a>
        
          <a class="recent-link" href="/blog/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%20plane/" title="" >
            <div class="recent-link-text">
              (no title)
            </div>
          </a>
        
          <a class="recent-link" href="/blog/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%20framebuffer/" title="" >
            <div class="recent-link-text">
              (no title)
            </div>
          </a>
        
          <a class="recent-link" href="/blog/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%20crtc/" title="" >
            <div class="recent-link-text">
              (no title)
            </div>
          </a>
        
      </ul>
    </div>
  </div>

    
  </div>
</sidebar>
    </div>
    <div id="content-body">
       

<article id="post-rk3399/Rockchip RK3399 - DRM plane" class="h-entry article article-type-post" itemprop="blogPost" itemscope itemtype="https://schema.org/BlogPosting">
  
    
   
  <div class="article-inner">
    <div class="article-main">
      <header class="article-header">
        
<div class="main-title-bar">
  <div class="main-title-dot"></div>
  
    
      <h1 class="p-name article-title" itemprop="headline name">
        Untitled
      </h1>
    
  
</div>

        <div class='meta-info-bar'>
          <div class="meta-info">
  <time class="dt-published" datetime="2023-09-11T12:23:16.222Z" itemprop="datePublished">2023-09-11</time>
</div>
          <div class="need-seperator meta-info">
            <div class="meta-cate-flex">
  
    Uncategorized 
   
</div>
  
          </div>
          <div class="wordcount need-seperator meta-info">
            6.2k words 
          </div>
        </div>
        
      </header>
      <div class="e-content article-entry" itemprop="articleBody">
        
          <h3 id="一、plane数据结构"><a href="#一、plane数据结构" class="headerlink" title="一、plane数据结构"></a>一、plane数据结构</h3><h4 id="1-1-struct-drm-plane"><a href="#1-1-struct-drm-plane" class="headerlink" title="1.1 struct drm_plane"></a>1.1 struct drm_plane</h4><p>linux内核使用struct drm_plane表示一个plane，它们从一个drm_framebuffer接收输入数据，并将其传递给一个drm_crtc。plane控制颜色转换，并且还参与输入像素的颜色转换。定义include&#x2F;drm&#x2F;drm_plane.h；</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br><span class="line">88</span><br><span class="line">89</span><br><span class="line">90</span><br><span class="line">91</span><br><span class="line">92</span><br><span class="line">93</span><br><span class="line">94</span><br><span class="line">95</span><br><span class="line">96</span><br><span class="line">97</span><br><span class="line">98</span><br><span class="line">99</span><br><span class="line">100</span><br><span class="line">101</span><br><span class="line">102</span><br><span class="line">103</span><br><span class="line">104</span><br><span class="line">105</span><br><span class="line">106</span><br><span class="line">107</span><br><span class="line">108</span><br><span class="line">109</span><br><span class="line">110</span><br><span class="line">111</span><br><span class="line">112</span><br><span class="line">113</span><br><span class="line">114</span><br><span class="line">115</span><br><span class="line">116</span><br><span class="line">117</span><br><span class="line">118</span><br><span class="line">119</span><br><span class="line">120</span><br><span class="line">121</span><br><span class="line">122</span><br><span class="line">123</span><br><span class="line">124</span><br><span class="line">125</span><br><span class="line">126</span><br><span class="line">127</span><br><span class="line">128</span><br><span class="line">129</span><br><span class="line">130</span><br><span class="line">131</span><br><span class="line">132</span><br><span class="line">133</span><br><span class="line">134</span><br><span class="line">135</span><br><span class="line">136</span><br><span class="line">137</span><br><span class="line">138</span><br><span class="line">139</span><br><span class="line">140</span><br><span class="line">141</span><br><span class="line">142</span><br><span class="line">143</span><br><span class="line">144</span><br><span class="line">145</span><br><span class="line">146</span><br><span class="line">147</span><br><span class="line">148</span><br><span class="line">149</span><br><span class="line">150</span><br><span class="line">151</span><br><span class="line">152</span><br><span class="line">153</span><br><span class="line">154</span><br><span class="line">155</span><br><span class="line">156</span><br><span class="line">157</span><br><span class="line">158</span><br><span class="line">159</span><br><span class="line">160</span><br><span class="line">161</span><br><span class="line">162</span><br><span class="line">163</span><br><span class="line">164</span><br><span class="line">165</span><br><span class="line">166</span><br><span class="line">167</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * struct drm_plane - central DRM plane control structure</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Planes represent the scanout hardware of a display block. They receive their</span></span><br><span class="line"><span class="comment"> * input data from a &amp;drm_framebuffer and feed it to a &amp;drm_crtc. Planes control</span></span><br><span class="line"><span class="comment"> * the color conversion, see `Plane Composition Properties`_ for more details,</span></span><br><span class="line"><span class="comment"> * and are also involved in the color conversion of input pixels, see `Color</span></span><br><span class="line"><span class="comment"> * Management Properties`_ for details on that.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="class"><span class="keyword">struct</span> <span class="title">drm_plane</span> &#123;</span></span><br><span class="line">        <span class="comment">/** @dev: DRM device this plane belongs to */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_device</span> *<span class="title">dev</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @head:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * List of all planes on @dev, linked from &amp;drm_mode_config.plane_list.</span></span><br><span class="line"><span class="comment">         * Invariant over the lifetime of @dev and therefore does not need</span></span><br><span class="line"><span class="comment">         * locking.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">list_head</span> <span class="title">head</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @name: human readable name, can be overwritten by the driver */</span></span><br><span class="line">        <span class="type">char</span> *name;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @mutex:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Protects modeset plane state, together with the &amp;drm_crtc.mutex of</span></span><br><span class="line"><span class="comment">         * CRTC this plane is linked to (when active, getting activated or</span></span><br><span class="line"><span class="comment">         * getting disabled).</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * For atomic drivers specifically this protects @state.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_modeset_lock</span> <span class="title">mutex</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @base: base mode object */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_mode_object</span> <span class="title">base</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @possible_crtcs: pipes this plane can be bound to constructed from</span></span><br><span class="line"><span class="comment">         * drm_crtc_mask()</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">uint32_t</span> possible_crtcs;</span><br><span class="line">        <span class="comment">/** @format_types: array of formats supported by this plane */</span></span><br><span class="line">        <span class="type">uint32_t</span> *format_types;</span><br><span class="line">        <span class="comment">/** @format_count: Size of the array pointed at by @format_types. */</span></span><br><span class="line">        <span class="type">unsigned</span> <span class="type">int</span> format_count;</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @format_default: driver hasn&#x27;t supplied supported formats for the</span></span><br><span class="line"><span class="comment">         * plane. Used by the non-atomic driver compatibility wrapper only.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">bool</span> format_default;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @modifiers: array of modifiers supported by this plane */</span></span><br><span class="line">        <span class="type">uint64_t</span> *modifiers;</span><br><span class="line">        <span class="comment">/** @modifier_count: Size of the array pointed at by @modifier_count. */</span></span><br><span class="line">        <span class="type">unsigned</span> <span class="type">int</span> modifier_count;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @crtc:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Currently bound CRTC, only meaningful for non-atomic drivers. For</span></span><br><span class="line"><span class="comment">         * atomic drivers this is forced to be NULL, atomic drivers should</span></span><br><span class="line"><span class="comment">         * instead check &amp;drm_plane_state.crtc.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_crtc</span> *<span class="title">crtc</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @fb:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Currently bound framebuffer, only meaningful for non-atomic drivers.</span></span><br><span class="line"><span class="comment">         * For atomic drivers this is forced to be NULL, atomic drivers should</span></span><br><span class="line"><span class="comment">         * instead check &amp;drm_plane_state.fb.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_framebuffer</span> *<span class="title">fb</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @old_fb:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Temporary tracking of the old fb while a modeset is ongoing. Only</span></span><br><span class="line"><span class="comment">         * used by non-atomic drivers, forced to be NULL for atomic drivers.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_framebuffer</span> *<span class="title">old_fb</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @funcs: plane control functions */</span></span><br><span class="line">        <span class="type">const</span> <span class="class"><span class="keyword">struct</span> <span class="title">drm_plane_funcs</span> *<span class="title">funcs</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @properties: property tracking for this plane */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_object_properties</span> <span class="title">properties</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @type: Type of plane, see &amp;enum drm_plane_type for details. */</span></span><br><span class="line">        <span class="class"><span class="keyword">enum</span> <span class="title">drm_plane_type</span> <span class="title">type</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @index: Position inside the mode_config.list, can be used as an array</span></span><br><span class="line"><span class="comment">         * index. It is invariant over the lifetime of the plane.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">unsigned</span> index;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @helper_private: mid-layer private data */</span></span><br><span class="line">        <span class="type">const</span> <span class="class"><span class="keyword">struct</span> <span class="title">drm_plane_helper_funcs</span> *<span class="title">helper_private</span>;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @state:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Current atomic state for this plane.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This is protected by @mutex. Note that nonblocking atomic commits</span></span><br><span class="line"><span class="comment">         * access the current plane state without taking locks. Either by going</span></span><br><span class="line"><span class="comment">         * through the &amp;struct drm_atomic_state pointers, see</span></span><br><span class="line"><span class="comment">         * for_each_oldnew_plane_in_state(), for_each_old_plane_in_state() and</span></span><br><span class="line"><span class="comment">         * for_each_new_plane_in_state(). Or through careful ordering of atomic</span></span><br><span class="line"><span class="comment">         * commit operations as implemented in the atomic helpers, see</span></span><br><span class="line"><span class="comment">         * &amp;struct drm_crtc_commit.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_plane_state</span> *<span class="title">state</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @alpha_property:</span></span><br><span class="line"><span class="comment">         * Optional alpha property for this plane. See</span></span><br><span class="line"><span class="comment">         * drm_plane_create_alpha_property().</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property</span> *<span class="title">alpha_property</span>;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @zpos_property:</span></span><br><span class="line"><span class="comment">         * Optional zpos property for this plane. See</span></span><br><span class="line"><span class="comment">         * drm_plane_create_zpos_property().</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property</span> *<span class="title">zpos_property</span>;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @rotation_property:</span></span><br><span class="line"><span class="comment">         * Optional rotation property for this plane. See</span></span><br><span class="line"><span class="comment">         * drm_plane_create_rotation_property().</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property</span> *<span class="title">rotation_property</span>;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @blend_mode_property:</span></span><br><span class="line"><span class="comment">         * Optional &quot;pixel blend mode&quot; enum property for this plane.</span></span><br><span class="line"><span class="comment">         * Blend mode property represents the alpha blending equation selection,</span></span><br><span class="line"><span class="comment">         * describing how the pixels from the current plane are composited with</span></span><br><span class="line"><span class="comment">         * the background.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property</span> *<span class="title">blend_mode_property</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @color_encoding_property:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Optional &quot;COLOR_ENCODING&quot; enum property for specifying</span></span><br><span class="line"><span class="comment">         * color encoding for non RGB formats.</span></span><br><span class="line"><span class="comment">         * See drm_plane_create_color_properties().</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property</span> *<span class="title">color_encoding_property</span>;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @color_range_property:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Optional &quot;COLOR_RANGE&quot; enum property for specifying</span></span><br><span class="line"><span class="comment">         * color range for non RGB formats.</span></span><br><span class="line"><span class="comment">         * See drm_plane_create_color_properties().</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property</span> *<span class="title">color_range_property</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @scaling_filter_property: property to apply a particular filter while</span></span><br><span class="line"><span class="comment">         * scaling.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property</span> *<span class="title">scaling_filter_property</span>;</span></span><br><span class="line">&#125;;</span><br></pre></td></tr></table></figure>

<p>该结构体包括以下成员：</p>
<ul>
<li>dev：该plane所属的DRM设备；</li>
<li>head：链表节点，用于将当前节点追加到drm_mode_config.plane_list链表；</li>
<li>name：可读性良好的名称，可以被驱动程序覆盖；</li>
<li>mutex：互斥锁，用于保存modset plane state；</li>
<li>base：struct drm_mode_object；</li>
<li>possible_crtcs：plane可以绑定到的管道，由drm_crtc_mask()构建；</li>
<li>format_types：plane支持的格式数组；</li>
<li>format_count：format_types数组的大小；</li>
<li>format_default：驱动程序没有为该plane提供支持的格式。仅由non-atomic driver兼容性包装器使用；</li>
<li>modifiers：该plane支持的修饰符数组；</li>
<li>modifier_count：modifiers数组的大小。</li>
<li>crtc：当前绑定的CRTC，仅对non-atomic driver有意义。对于atomic driver，它被强制为NULL，atomic driver应该检查drm_plane_state.crtc；</li>
<li>fb：当前绑定的帧缓冲，仅对non-atomic driver有意义。对于atomic driver，它被强制为NULL，atomic driver应该检查drm_plane_state.fb；</li>
<li>old_fb：在模式设置进行中临时跟踪旧的帧缓冲。仅由non-atomic driver使用，对于atomic driver，它被强制为NULL；</li>
<li>funcs：plane控制函数；</li>
<li>properties：用于跟踪plane的属性。</li>
<li>type：plane的类型，详见enum drm_plane_type；</li>
<li>index：在mode_config.list中的位置，可用作数组索引。在plane的生命周期中保持不变；</li>
<li>helper_private：中间层私有数据；</li>
<li>state：当前的原子状态；</li>
<li>alpha_property：表示plane的可选alpha属性，参见drm_plane_create_alpha_property()；</li>
<li>zpos_property：表示plane的可选zpos属性，参见drm_plane_create_zpos_property()；</li>
<li>rotation_property：表示plane的可选旋转属性，参见drm_plane_create_rotation_property()；</li>
<li>blend_mode_property：表示plane的可选pixel blend mode枚举属性；</li>
<li>color_encoding_property：表示plane的可选COLOR_ENCODING枚举属性，用于指定非RGB格式的颜色编码。参见drm_plane_create_color_properties()；</li>
<li>color_range_property：表示plane的可选COLOR_RANGE枚举属性，用于指定非RGB格式的颜色范围。参见drm_plane_create_color_properties()；</li>
<li>scaling_filter_property：用于在缩放时应用特定滤镜的属性；</li>
</ul>
<h5 id="1-1-1-plane类型"><a href="#1-1-1-plane类型" class="headerlink" title="1.1.1 plane类型"></a>1.1.1 plane类型</h5><p>plane的类型定义在include&#x2F;drm&#x2F;drm_plane.h；</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * enum drm_plane_type - uapi plane type enumeration</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * For historical reasons not all planes are made the same. This enumeration is</span></span><br><span class="line"><span class="comment"> * used to tell the different types of planes apart to implement the different</span></span><br><span class="line"><span class="comment"> * uapi semantics for them. For userspace which is universal plane aware and</span></span><br><span class="line"><span class="comment"> * which is using that atomic IOCTL there&#x27;s no difference between these planes</span></span><br><span class="line"><span class="comment"> * (beyong what the driver and hardware can support of course).</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * For compatibility with legacy userspace, only overlay planes are made</span></span><br><span class="line"><span class="comment"> * available to userspace by default. Userspace clients may set the</span></span><br><span class="line"><span class="comment"> * &amp;DRM_CLIENT_CAP_UNIVERSAL_PLANES client capability bit to indicate that they</span></span><br><span class="line"><span class="comment"> * wish to receive a universal plane list containing all plane types. See also</span></span><br><span class="line"><span class="comment"> * drm_for_each_legacy_plane().</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * In addition to setting each plane&#x27;s type, drivers need to setup the</span></span><br><span class="line"><span class="comment"> * &amp;drm_crtc.primary and optionally &amp;drm_crtc.cursor pointers for legacy</span></span><br><span class="line"><span class="comment"> * IOCTLs. See drm_crtc_init_with_planes().</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * WARNING: The values of this enum is UABI since they&#x27;re exposed in the &quot;type&quot;</span></span><br><span class="line"><span class="comment"> * property.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="class"><span class="keyword">enum</span> <span class="title">drm_plane_type</span> &#123;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @DRM_PLANE_TYPE_OVERLAY:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Overlay planes represent all non-primary, non-cursor planes. Some</span></span><br><span class="line"><span class="comment">         * drivers refer to these types of planes as &quot;sprites&quot; internally.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        DRM_PLANE_TYPE_OVERLAY,</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @DRM_PLANE_TYPE_PRIMARY:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * A primary plane attached to a CRTC is the most likely to be able to</span></span><br><span class="line"><span class="comment">         * light up the CRTC when no scaling/cropping is used and the plane</span></span><br><span class="line"><span class="comment">         * covers the whole CRTC.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        DRM_PLANE_TYPE_PRIMARY,</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @DRM_PLANE_TYPE_CURSOR:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * A cursor plane attached to a CRTC is more likely to be able to be</span></span><br><span class="line"><span class="comment">         * enabled when no scaling/cropping is used and the framebuffer has the</span></span><br><span class="line"><span class="comment">         * size indicated by &amp;drm_mode_config.cursor_width and</span></span><br><span class="line"><span class="comment">         * &amp;drm_mode_config.cursor_height. Additionally, if the driver doesn&#x27;t</span></span><br><span class="line"><span class="comment">         * support modifiers, the framebuffer should have a linear layout.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        DRM_PLANE_TYPE_CURSOR,</span><br><span class="line">&#125;;</span><br></pre></td></tr></table></figure>

<h5 id="1-1-2-plane状态"><a href="#1-1-2-plane状态" class="headerlink" title="1.1.2 plane状态"></a>1.1.2 plane状态</h5><p>struct drm_plane_state用于表示plane的状态，定义在include&#x2F;drm&#x2F;drm_plane.h；</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br><span class="line">88</span><br><span class="line">89</span><br><span class="line">90</span><br><span class="line">91</span><br><span class="line">92</span><br><span class="line">93</span><br><span class="line">94</span><br><span class="line">95</span><br><span class="line">96</span><br><span class="line">97</span><br><span class="line">98</span><br><span class="line">99</span><br><span class="line">100</span><br><span class="line">101</span><br><span class="line">102</span><br><span class="line">103</span><br><span class="line">104</span><br><span class="line">105</span><br><span class="line">106</span><br><span class="line">107</span><br><span class="line">108</span><br><span class="line">109</span><br><span class="line">110</span><br><span class="line">111</span><br><span class="line">112</span><br><span class="line">113</span><br><span class="line">114</span><br><span class="line">115</span><br><span class="line">116</span><br><span class="line">117</span><br><span class="line">118</span><br><span class="line">119</span><br><span class="line">120</span><br><span class="line">121</span><br><span class="line">122</span><br><span class="line">123</span><br><span class="line">124</span><br><span class="line">125</span><br><span class="line">126</span><br><span class="line">127</span><br><span class="line">128</span><br><span class="line">129</span><br><span class="line">130</span><br><span class="line">131</span><br><span class="line">132</span><br><span class="line">133</span><br><span class="line">134</span><br><span class="line">135</span><br><span class="line">136</span><br><span class="line">137</span><br><span class="line">138</span><br><span class="line">139</span><br><span class="line">140</span><br><span class="line">141</span><br><span class="line">142</span><br><span class="line">143</span><br><span class="line">144</span><br><span class="line">145</span><br><span class="line">146</span><br><span class="line">147</span><br><span class="line">148</span><br><span class="line">149</span><br><span class="line">150</span><br><span class="line">151</span><br><span class="line">152</span><br><span class="line">153</span><br><span class="line">154</span><br><span class="line">155</span><br><span class="line">156</span><br><span class="line">157</span><br><span class="line">158</span><br><span class="line">159</span><br><span class="line">160</span><br><span class="line">161</span><br><span class="line">162</span><br><span class="line">163</span><br><span class="line">164</span><br><span class="line">165</span><br><span class="line">166</span><br><span class="line">167</span><br><span class="line">168</span><br><span class="line">169</span><br><span class="line">170</span><br><span class="line">171</span><br><span class="line">172</span><br><span class="line">173</span><br><span class="line">174</span><br><span class="line">175</span><br><span class="line">176</span><br><span class="line">177</span><br><span class="line">178</span><br><span class="line">179</span><br><span class="line">180</span><br><span class="line">181</span><br><span class="line">182</span><br><span class="line">183</span><br><span class="line">184</span><br><span class="line">185</span><br><span class="line">186</span><br><span class="line">187</span><br><span class="line">188</span><br><span class="line">189</span><br><span class="line">190</span><br><span class="line">191</span><br><span class="line">192</span><br><span class="line">193</span><br><span class="line">194</span><br><span class="line">195</span><br><span class="line">196</span><br><span class="line">197</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * struct drm_plane_state - mutable plane state</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Please note that the destination coordinates @crtc_x, @crtc_y, @crtc_h and</span></span><br><span class="line"><span class="comment"> * @crtc_w and the source coordinates @src_x, @src_y, @src_h and @src_w are the</span></span><br><span class="line"><span class="comment"> * raw coordinates provided by userspace. Drivers should use</span></span><br><span class="line"><span class="comment"> * drm_atomic_helper_check_plane_state() and only use the derived rectangles in</span></span><br><span class="line"><span class="comment"> * @src and @dst to program the hardware.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="class"><span class="keyword">struct</span> <span class="title">drm_plane_state</span> &#123;</span></span><br><span class="line">        <span class="comment">/** @plane: backpointer to the plane */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_plane</span> *<span class="title">plane</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @crtc:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Currently bound CRTC, NULL if disabled. Do not this write directly,</span></span><br><span class="line"><span class="comment">         * use drm_atomic_set_crtc_for_plane()</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_crtc</span> *<span class="title">crtc</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @fb:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Currently bound framebuffer. Do not write this directly, use</span></span><br><span class="line"><span class="comment">         * drm_atomic_set_fb_for_plane()</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_framebuffer</span> *<span class="title">fb</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @fence:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Optional fence to wait for before scanning out @fb. The core atomic</span></span><br><span class="line"><span class="comment">         * code will set this when userspace is using explicit fencing. Do not</span></span><br><span class="line"><span class="comment">         * write this field directly for a driver&#x27;s implicit fence.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers should store any implicit fence in this from their</span></span><br><span class="line"><span class="comment">         * &amp;drm_plane_helper_funcs.prepare_fb callback. See</span></span><br><span class="line"><span class="comment">         * drm_gem_plane_helper_prepare_fb() for a suitable helper.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">dma_fence</span> *<span class="title">fence</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @crtc_x:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Left position of visible portion of plane on crtc, signed dest</span></span><br><span class="line"><span class="comment">         * location allows it to be partially off screen.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line"></span><br><span class="line">        <span class="type">int32_t</span> crtc_x;</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @crtc_y:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Upper position of visible portion of plane on crtc, signed dest</span></span><br><span class="line"><span class="comment">         * location allows it to be partially off screen.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int32_t</span> crtc_y;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @crtc_w: width of visible portion of plane on crtc */</span></span><br><span class="line">        <span class="comment">/** @crtc_h: height of visible portion of plane on crtc */</span></span><br><span class="line">        <span class="type">uint32_t</span> crtc_w, crtc_h;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @src_x: left position of visible portion of plane within plane (in</span></span><br><span class="line"><span class="comment">         * 16.16 fixed point).</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">uint32_t</span> src_x;</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @src_y: upper position of visible portion of plane within plane (in</span></span><br><span class="line"><span class="comment">         * 16.16 fixed point).</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">uint32_t</span> src_y;</span><br><span class="line">        <span class="comment">/** @src_w: width of visible portion of plane (in 16.16) */</span></span><br><span class="line">        <span class="comment">/** @src_h: height of visible portion of plane (in 16.16) */</span></span><br><span class="line">        <span class="type">uint32_t</span> src_h, src_w;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @alpha:</span></span><br><span class="line"><span class="comment">         * Opacity of the plane with 0 as completely transparent and 0xffff as</span></span><br><span class="line"><span class="comment">         * completely opaque. See drm_plane_create_alpha_property() for more</span></span><br><span class="line"><span class="comment">         * details.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        u16 alpha;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @pixel_blend_mode:</span></span><br><span class="line"><span class="comment">         * The alpha blending equation selection, describing how the pixels from</span></span><br><span class="line"><span class="comment">         * the current plane are composited with the background. Value can be</span></span><br><span class="line"><span class="comment">         * one of DRM_MODE_BLEND_*</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">uint16_t</span> pixel_blend_mode;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @rotation:</span></span><br><span class="line"><span class="comment">         * Rotation of the plane. See drm_plane_create_rotation_property() for</span></span><br><span class="line"><span class="comment">         * more details.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">unsigned</span> <span class="type">int</span> rotation;</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @zpos:</span></span><br><span class="line"><span class="comment">         * Priority of the given plane on crtc (optional).</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * User-space may set mutable zpos properties so that multiple active</span></span><br><span class="line"><span class="comment">         * planes on the same CRTC have identical zpos values. This is a</span></span><br><span class="line"><span class="comment">         * user-space bug, but drivers can solve the conflict by comparing the</span></span><br><span class="line"><span class="comment">         * plane object IDs; the plane with a higher ID is stacked on top of a</span></span><br><span class="line"><span class="comment">         * plane with a lower ID.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * See drm_plane_create_zpos_property() and</span></span><br><span class="line"><span class="comment">         * drm_plane_create_zpos_immutable_property() for more details.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">unsigned</span> <span class="type">int</span> zpos;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @normalized_zpos:</span></span><br><span class="line"><span class="comment">         * Normalized value of zpos: unique, range from 0 to N-1 where N is the</span></span><br><span class="line"><span class="comment">         * number of active planes for given crtc. Note that the driver must set</span></span><br><span class="line"><span class="comment">         * &amp;drm_mode_config.normalize_zpos or call drm_atomic_normalize_zpos() to</span></span><br><span class="line"><span class="comment">         * update this before it can be trusted.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">unsigned</span> <span class="type">int</span> normalized_zpos;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @color_encoding:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Color encoding for non RGB formats</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">enum</span> <span class="title">drm_color_encoding</span> <span class="title">color_encoding</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @color_range:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Color range for non RGB formats</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">enum</span> <span class="title">drm_color_range</span> <span class="title">color_range</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @fb_damage_clips:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Blob representing damage (area in plane framebuffer that changed</span></span><br><span class="line"><span class="comment">         * since last plane update) as an array of &amp;drm_mode_rect in framebuffer</span></span><br><span class="line"><span class="comment">         * coodinates of the attached framebuffer. Note that unlike plane src,</span></span><br><span class="line"><span class="comment">         * damage clips are not in 16.16 fixed point.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * See drm_plane_get_damage_clips() and</span></span><br><span class="line"><span class="comment">         * drm_plane_get_damage_clips_count() for accessing these.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_property_blob</span> *<span class="title">fb_damage_clips</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @src:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * source coordinates of the plane (in 16.16).</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * When using drm_atomic_helper_check_plane_state(),</span></span><br><span class="line"><span class="comment">         * the coordinates are clipped, but the driver may choose</span></span><br><span class="line"><span class="comment">         * to use unclipped coordinates instead when the hardware</span></span><br><span class="line"><span class="comment">         * performs the clipping automatically.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @dst:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * clipped destination coordinates of the plane.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * When using drm_atomic_helper_check_plane_state(),</span></span><br><span class="line"><span class="comment">         * the coordinates are clipped, but the driver may choose</span></span><br><span class="line"><span class="comment">         * to use unclipped coordinates instead when the hardware</span></span><br><span class="line"><span class="comment">         * performs the clipping automatically.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_rect</span> <span class="title">src</span>, <span class="title">dst</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @visible:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Visibility of the plane. This can be false even if fb!=NULL and</span></span><br><span class="line"><span class="comment">         * crtc!=NULL, due to clipping.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">bool</span> visible;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @scaling_filter:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Scaling filter to be applied</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">enum</span> <span class="title">drm_scaling_filter</span> <span class="title">scaling_filter</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @commit: Tracks the pending commit to prevent use-after-free conditions,</span></span><br><span class="line"><span class="comment">         * and for async plane updates.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * May be NULL.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_crtc_commit</span> *<span class="title">commit</span>;</span></span><br><span class="line"></span><br><span class="line">        <span class="comment">/** @state: backpointer to global drm_atomic_state */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_atomic_state</span> *<span class="title">state</span>;</span></span><br><span class="line">&#125;;</span><br></pre></td></tr></table></figure>

<h4 id="1-2-操作函数"><a href="#1-2-操作函数" class="headerlink" title="1.2 操作函数"></a>1.2 操作函数</h4><h5 id="1-2-1-struct-drm-plane-funcs"><a href="#1-2-1-struct-drm-plane-funcs" class="headerlink" title="1.2.1  struct drm_plane_funcs"></a>1.2.1  struct drm_plane_funcs</h5><p> struct drm_plane_funcs用于描述plane的控制函数，定义在include&#x2F;drm&#x2F;drm_plane.h；</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br><span class="line">88</span><br><span class="line">89</span><br><span class="line">90</span><br><span class="line">91</span><br><span class="line">92</span><br><span class="line">93</span><br><span class="line">94</span><br><span class="line">95</span><br><span class="line">96</span><br><span class="line">97</span><br><span class="line">98</span><br><span class="line">99</span><br><span class="line">100</span><br><span class="line">101</span><br><span class="line">102</span><br><span class="line">103</span><br><span class="line">104</span><br><span class="line">105</span><br><span class="line">106</span><br><span class="line">107</span><br><span class="line">108</span><br><span class="line">109</span><br><span class="line">110</span><br><span class="line">111</span><br><span class="line">112</span><br><span class="line">113</span><br><span class="line">114</span><br><span class="line">115</span><br><span class="line">116</span><br><span class="line">117</span><br><span class="line">118</span><br><span class="line">119</span><br><span class="line">120</span><br><span class="line">121</span><br><span class="line">122</span><br><span class="line">123</span><br><span class="line">124</span><br><span class="line">125</span><br><span class="line">126</span><br><span class="line">127</span><br><span class="line">128</span><br><span class="line">129</span><br><span class="line">130</span><br><span class="line">131</span><br><span class="line">132</span><br><span class="line">133</span><br><span class="line">134</span><br><span class="line">135</span><br><span class="line">136</span><br><span class="line">137</span><br><span class="line">138</span><br><span class="line">139</span><br><span class="line">140</span><br><span class="line">141</span><br><span class="line">142</span><br><span class="line">143</span><br><span class="line">144</span><br><span class="line">145</span><br><span class="line">146</span><br><span class="line">147</span><br><span class="line">148</span><br><span class="line">149</span><br><span class="line">150</span><br><span class="line">151</span><br><span class="line">152</span><br><span class="line">153</span><br><span class="line">154</span><br><span class="line">155</span><br><span class="line">156</span><br><span class="line">157</span><br><span class="line">158</span><br><span class="line">159</span><br><span class="line">160</span><br><span class="line">161</span><br><span class="line">162</span><br><span class="line">163</span><br><span class="line">164</span><br><span class="line">165</span><br><span class="line">166</span><br><span class="line">167</span><br><span class="line">168</span><br><span class="line">169</span><br><span class="line">170</span><br><span class="line">171</span><br><span class="line">172</span><br><span class="line">173</span><br><span class="line">174</span><br><span class="line">175</span><br><span class="line">176</span><br><span class="line">177</span><br><span class="line">178</span><br><span class="line">179</span><br><span class="line">180</span><br><span class="line">181</span><br><span class="line">182</span><br><span class="line">183</span><br><span class="line">184</span><br><span class="line">185</span><br><span class="line">186</span><br><span class="line">187</span><br><span class="line">188</span><br><span class="line">189</span><br><span class="line">190</span><br><span class="line">191</span><br><span class="line">192</span><br><span class="line">193</span><br><span class="line">194</span><br><span class="line">195</span><br><span class="line">196</span><br><span class="line">197</span><br><span class="line">198</span><br><span class="line">199</span><br><span class="line">200</span><br><span class="line">201</span><br><span class="line">202</span><br><span class="line">203</span><br><span class="line">204</span><br><span class="line">205</span><br><span class="line">206</span><br><span class="line">207</span><br><span class="line">208</span><br><span class="line">209</span><br><span class="line">210</span><br><span class="line">211</span><br><span class="line">212</span><br><span class="line">213</span><br><span class="line">214</span><br><span class="line">215</span><br><span class="line">216</span><br><span class="line">217</span><br><span class="line">218</span><br><span class="line">219</span><br><span class="line">220</span><br><span class="line">221</span><br><span class="line">222</span><br><span class="line">223</span><br><span class="line">224</span><br><span class="line">225</span><br><span class="line">226</span><br><span class="line">227</span><br><span class="line">228</span><br><span class="line">229</span><br><span class="line">230</span><br><span class="line">231</span><br><span class="line">232</span><br><span class="line">233</span><br><span class="line">234</span><br><span class="line">235</span><br><span class="line">236</span><br><span class="line">237</span><br><span class="line">238</span><br><span class="line">239</span><br><span class="line">240</span><br><span class="line">241</span><br><span class="line">242</span><br><span class="line">243</span><br><span class="line">244</span><br><span class="line">245</span><br><span class="line">246</span><br><span class="line">247</span><br><span class="line">248</span><br><span class="line">249</span><br><span class="line">250</span><br><span class="line">251</span><br><span class="line">252</span><br><span class="line">253</span><br><span class="line">254</span><br><span class="line">255</span><br><span class="line">256</span><br><span class="line">257</span><br><span class="line">258</span><br><span class="line">259</span><br><span class="line">260</span><br><span class="line">261</span><br><span class="line">262</span><br><span class="line">263</span><br><span class="line">264</span><br><span class="line">265</span><br><span class="line">266</span><br><span class="line">267</span><br><span class="line">268</span><br><span class="line">269</span><br><span class="line">270</span><br><span class="line">271</span><br><span class="line">272</span><br><span class="line">273</span><br><span class="line">274</span><br><span class="line">275</span><br><span class="line">276</span><br><span class="line">277</span><br><span class="line">278</span><br><span class="line">279</span><br><span class="line">280</span><br><span class="line">281</span><br><span class="line">282</span><br><span class="line">283</span><br><span class="line">284</span><br><span class="line">285</span><br><span class="line">286</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * struct drm_plane_funcs - driver plane control functions</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="class"><span class="keyword">struct</span> <span class="title">drm_plane_funcs</span> &#123;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @update_plane:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This is the legacy entry point to enable and configure the plane for</span></span><br><span class="line"><span class="comment">         * the given CRTC and framebuffer. It is never called to disable the</span></span><br><span class="line"><span class="comment">         * plane, i.e. the passed-in crtc and fb paramters are never NULL.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * The source rectangle in frame buffer memory coordinates is given by</span></span><br><span class="line"><span class="comment">         * the src_x, src_y, src_w and src_h parameters (as 16.16 fixed point</span></span><br><span class="line"><span class="comment">         * values). Devices that don&#x27;t support subpixel plane coordinates can</span></span><br><span class="line"><span class="comment">         * ignore the fractional part.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * The destination rectangle in CRTC coordinates is given by the</span></span><br><span class="line"><span class="comment">         * crtc_x, crtc_y, crtc_w and crtc_h parameters (as integer values).</span></span><br><span class="line"><span class="comment">         * Devices scale the source rectangle to the destination rectangle. If</span></span><br><span class="line"><span class="comment">         * scaling is not supported, and the source rectangle size doesn&#x27;t match</span></span><br><span class="line"><span class="comment">         * the destination rectangle size, the driver must return a</span></span><br><span class="line"><span class="comment">         * -&lt;errorname&gt;EINVAL&lt;/errorname&gt; error.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers implementing atomic modeset should use</span></span><br><span class="line"><span class="comment">         * drm_atomic_helper_update_plane() to implement this hook.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success or a negative error code on failure.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*update_plane)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                            <span class="keyword">struct</span> drm_crtc *crtc, <span class="keyword">struct</span> drm_framebuffer *fb,</span><br><span class="line">                            <span class="type">int</span> crtc_x, <span class="type">int</span> crtc_y,</span><br><span class="line">                            <span class="type">unsigned</span> <span class="type">int</span> crtc_w, <span class="type">unsigned</span> <span class="type">int</span> crtc_h,</span><br><span class="line">                            <span class="type">uint32_t</span> src_x, <span class="type">uint32_t</span> src_y,</span><br><span class="line">                            <span class="type">uint32_t</span> src_w, <span class="type">uint32_t</span> src_h,</span><br><span class="line">                            <span class="keyword">struct</span> drm_modeset_acquire_ctx *ctx);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @disable_plane:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This is the legacy entry point to disable the plane. The DRM core</span></span><br><span class="line"><span class="comment">         * calls this method in response to a DRM_IOCTL_MODE_SETPLANE IOCTL call</span></span><br><span class="line"><span class="comment">         * with the frame buffer ID set to 0.  Disabled planes must not be</span></span><br><span class="line"><span class="comment">         * processed by the CRTC.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers implementing atomic modeset should use</span></span><br><span class="line"><span class="comment">         * drm_atomic_helper_disable_plane() to implement this hook.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success or a negative error code on failure.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*update_plane)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                            <span class="keyword">struct</span> drm_crtc *crtc, <span class="keyword">struct</span> drm_framebuffer *fb,</span><br><span class="line">                            <span class="type">int</span> crtc_x, <span class="type">int</span> crtc_y,</span><br><span class="line">                            <span class="type">unsigned</span> <span class="type">int</span> crtc_w, <span class="type">unsigned</span> <span class="type">int</span> crtc_h,</span><br><span class="line">                            <span class="type">uint32_t</span> src_x, <span class="type">uint32_t</span> src_y,</span><br><span class="line">                            <span class="type">uint32_t</span> src_w, <span class="type">uint32_t</span> src_h,</span><br><span class="line">                            <span class="keyword">struct</span> drm_modeset_acquire_ctx *ctx);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @disable_plane:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This is the legacy entry point to disable the plane. The DRM core</span></span><br><span class="line"><span class="comment">         * calls this method in response to a DRM_IOCTL_MODE_SETPLANE IOCTL call</span></span><br><span class="line"><span class="comment">         * with the frame buffer ID set to 0.  Disabled planes must not be</span></span><br><span class="line"><span class="comment">         * processed by the CRTC.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers implementing atomic modeset should use</span></span><br><span class="line"><span class="comment">         * drm_atomic_helper_disable_plane() to implement this hook.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success or a negative error code on failure.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*disable_plane)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                             <span class="keyword">struct</span> drm_modeset_acquire_ctx *ctx);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @destroy:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Clean up plane resources. This is only called at driver unload time</span></span><br><span class="line"><span class="comment">         * through drm_mode_config_cleanup() since a plane cannot be hotplugged</span></span><br><span class="line"><span class="comment">         * in DRM.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*destroy)(<span class="keyword">struct</span> drm_plane *plane);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @reset:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Reset plane hardware and software state to off. This function isn&#x27;t</span></span><br><span class="line"><span class="comment">         * called by the core directly, only through drm_mode_config_reset().</span></span><br><span class="line"><span class="comment">         * It&#x27;s not a helper hook only for historical reasons.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Atomic drivers can use drm_atomic_helper_plane_reset() to reset</span></span><br><span class="line"><span class="comment">         * atomic state using this hook.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*reset)(<span class="keyword">struct</span> drm_plane *plane);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @set_property:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This is the legacy entry point to update a property attached to the</span></span><br><span class="line"><span class="comment">         * plane.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is optional if the driver does not support any legacy</span></span><br><span class="line"><span class="comment">         * driver-private properties. For atomic drivers it is not used because</span></span><br><span class="line"><span class="comment">         * property handling is done entirely in the DRM core.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success or a negative error code on failure.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*set_property)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                            <span class="keyword">struct</span> drm_property *property, <span class="type">uint64_t</span> val);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_duplicate_state:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Duplicate the current atomic state for this plane and return it.</span></span><br><span class="line"><span class="comment">         * The core and helpers guarantee that any atomic state duplicated with</span></span><br><span class="line"><span class="comment">         * this hook and still owned by the caller (i.e. not transferred to the</span></span><br><span class="line"><span class="comment">         * driver by calling &amp;drm_mode_config_funcs.atomic_commit) will be</span></span><br><span class="line"><span class="comment">         * cleaned up by calling the @atomic_destroy_state hook in this</span></span><br><span class="line"><span class="comment">         * structure.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is mandatory for atomic drivers.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Atomic drivers which don&#x27;t subclass &amp;struct drm_plane_state should use</span></span><br><span class="line"><span class="comment">         * drm_atomic_helper_plane_duplicate_state(). Drivers that subclass the</span></span><br><span class="line"><span class="comment">         * state structure to extend it with driver-private state should use</span></span><br><span class="line"><span class="comment">         * __drm_atomic_helper_plane_duplicate_state() to make sure shared state is</span></span><br><span class="line"><span class="comment">         * duplicated in a consistent fashion across drivers.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * It is an error to call this hook before &amp;drm_plane.state has been</span></span><br><span class="line"><span class="comment">         * initialized correctly.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * <span class="doctag">NOTE:</span></span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * If the duplicate state references refcounted resources this hook must</span></span><br><span class="line"><span class="comment">         * acquire a reference for each of them. The driver must release these</span></span><br><span class="line"><span class="comment">         * references again in @atomic_destroy_state.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Duplicated atomic state or NULL when the allocation failed.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_plane_state</span> *(*<span class="title">atomic_duplicate_state</span>)(<span class="keyword">struct</span> <span class="title">drm_plane</span> *<span class="title">plane</span>);</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_destroy_state:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Destroy a state duplicated with @atomic_duplicate_state and release</span></span><br><span class="line"><span class="comment">         * or unreference all resources it references</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is mandatory for atomic drivers.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*atomic_destroy_state)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                                     <span class="keyword">struct</span> drm_plane_state *state);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_set_property:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Decode a driver-private property value and store the decoded value</span></span><br><span class="line"><span class="comment">         * into the passed-in state structure. Since the atomic core decodes all</span></span><br><span class="line"><span class="comment">         * standardized properties (even for extensions beyond the core set of</span></span><br><span class="line"><span class="comment">         * properties which might not be implemented by all drivers) this</span></span><br><span class="line"><span class="comment">         * requires drivers to subclass the state structure.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Such driver-private properties should really only be implemented for</span></span><br><span class="line"><span class="comment">         * truly hardware/vendor specific state. Instead it is preferred to</span></span><br><span class="line"><span class="comment">         * standardize atomic extension and decode the properties used to expose</span></span><br><span class="line"><span class="comment">         * such an extension in the core.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Do not call this function directly, use</span></span><br><span class="line"><span class="comment">         * drm_atomic_plane_set_property() instead.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is optional if the driver does not support any</span></span><br><span class="line"><span class="comment">         * driver-private atomic properties.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * <span class="doctag">NOTE:</span></span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This function is called in the state assembly phase of atomic</span></span><br><span class="line"><span class="comment">         * modesets, which can be aborted for any reason (including on</span></span><br><span class="line"><span class="comment">         * userspace&#x27;s request to just check whether a configuration would be</span></span><br><span class="line"><span class="comment">         * possible). Drivers MUST NOT touch any persistent state (hardware or</span></span><br><span class="line"><span class="comment">         * software) or data structures except the passed in @state parameter.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Also since userspace controls in which order properties are set this</span></span><br><span class="line"><span class="comment">         * function must not do any input validation (since the state update is</span></span><br><span class="line"><span class="comment">         * incomplete and hence likely inconsistent). Instead any such input</span></span><br><span class="line"><span class="comment">         * validation must be done in the various atomic_check callbacks.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 if the property has been found, -EINVAL if the property isn&#x27;t</span></span><br><span class="line"><span class="comment">         * implemented by the driver (which shouldn&#x27;t ever happen, the core only</span></span><br><span class="line"><span class="comment">         * asks for properties attached to this plane). No other validation is</span></span><br><span class="line"><span class="comment">         * allowed by the driver. The core already checks that the property</span></span><br><span class="line"><span class="comment">         * value is within the range (integer, valid enum value, ...) the driver</span></span><br><span class="line"><span class="comment">         * set when registering the property.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*atomic_set_property)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                                   <span class="keyword">struct</span> drm_plane_state *state,</span><br><span class="line">                                   <span class="keyword">struct</span> drm_property *property,</span><br><span class="line">                                   <span class="type">uint64_t</span> val);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_get_property:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Reads out the decoded driver-private property. This is used to</span></span><br><span class="line"><span class="comment">         * implement the GETPLANE IOCTL.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Do not call this function directly, use</span></span><br><span class="line"><span class="comment">         * drm_atomic_plane_get_property() instead.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is optional if the driver does not support any</span></span><br><span class="line"><span class="comment">         * driver-private atomic properties.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success, -EINVAL if the property isn&#x27;t implemented by the</span></span><br><span class="line"><span class="comment">         * driver (which should never happen, the core only asks for</span></span><br><span class="line"><span class="comment">         * properties attached to this plane).</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*atomic_get_property)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                                   <span class="type">const</span> <span class="keyword">struct</span> drm_plane_state *state,</span><br><span class="line">                                   <span class="keyword">struct</span> drm_property *property,</span><br><span class="line">                                   <span class="type">uint64_t</span> *val);</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @late_register:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This optional hook can be used to register additional userspace</span></span><br><span class="line"><span class="comment">         * interfaces attached to the plane like debugfs interfaces.</span></span><br><span class="line"><span class="comment">         * It is called late in the driver load sequence from drm_dev_register().</span></span><br><span class="line"><span class="comment">         * Everything added from this callback should be unregistered in</span></span><br><span class="line"><span class="comment">         * the early_unregister callback.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Returns:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success, or a negative error code on failure.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*late_register)(<span class="keyword">struct</span> drm_plane *plane);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @early_unregister:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This optional hook should be used to unregister the additional</span></span><br><span class="line"><span class="comment">         * userspace interfaces attached to the plane from</span></span><br><span class="line"><span class="comment">         * @late_register. It is called from drm_dev_unregister(),</span></span><br><span class="line"><span class="comment">         * early in the driver unload sequence to disable userspace access</span></span><br><span class="line"><span class="comment">         * before data structures are torndown.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*early_unregister)(<span class="keyword">struct</span> drm_plane *plane);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_print_state:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * If driver subclasses &amp;struct drm_plane_state, it should implement</span></span><br><span class="line"><span class="comment">         * this optional hook for printing additional driver specific state.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Do not call this directly, use drm_atomic_plane_print_state()</span></span><br><span class="line"><span class="comment">         * instead.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*atomic_print_state)(<span class="keyword">struct</span> drm_printer *p,</span><br><span class="line">                                   <span class="type">const</span> <span class="keyword">struct</span> drm_plane_state *state);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @format_mod_supported:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This optional hook is used for the DRM to determine if the given</span></span><br><span class="line"><span class="comment">         * format/modifier combination is valid for the plane. This allows the</span></span><br><span class="line"><span class="comment">         * DRM to generate the correct format bitmask (which formats apply to</span></span><br><span class="line"><span class="comment">         * which modifier), and to validate modifiers at atomic_check time.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * If not present, then any modifier in the plane&#x27;s modifier</span></span><br><span class="line"><span class="comment">         * list is allowed with any of the plane&#x27;s formats.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Returns:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * True if the given modifier is valid for that format on the plane.</span></span><br><span class="line"><span class="comment">         * False otherwise.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">bool</span> (*format_mod_supported)(<span class="keyword">struct</span> drm_plane *plane, <span class="type">uint32_t</span> format,</span><br><span class="line">                                            <span class="type">uint64_t</span> modifier);</span><br><span class="line">&#125;;</span><br></pre></td></tr></table></figure>

<p>这里定义了一大堆回调函数：</p>
<ul>
<li>update_plane：这个函数已经过时了，为给定的CRTC和framebuffer启用并配置plane；</li>
<li>disable_plane：这个函数也过时了，用于禁用plane；</li>
<li>destroy：用于清理plane的所有资源；在驱动卸载时调用drm_mode_config_cleanup()函数时会被回调；</li>
<li>reset：用于将plane硬件和软件重置为关闭状态，这个函数不会直接调用，只会通过drm_mode_config_reset()调用；</li>
<li>set_property：这个函数也过时了，用于更新plane的property；</li>
<li>atomic_duplicate_state：用于复制当前的plane状态并返回；</li>
<li>atomic_destroy_state：销毁使用atomic_duplicate_state复制的状态，并释放或取消引用其引用的所有资源；</li>
<li>atomic_set_property：原子操作用于设置plane的property；</li>
<li>atomic_get_property：原子操作用户获取plane的property；</li>
<li>late_register：可选的钩子函数，会被drm_dev_register()函数调用，可以用来为plane注册额外的用户空间接口，比如debugfs；</li>
<li>early_unregister：可选的钩子函数，会被drm_dev_unregister()函数调用，可以用来为卸载在用户空间通过late_register()注册的接口；</li>
<li>atomic_print_state：该函数需要通过drm_atomic_plane_print_state()调用；</li>
<li>format_mod_supported：可选的钩子函数，用于确定给定的format&#x2F;modifier组合是否对plane有效；</li>
</ul>
<h5 id="1-2-2-struct-drm-plane-helper-funcs"><a href="#1-2-2-struct-drm-plane-helper-funcs" class="headerlink" title="1.2.2 struct drm_plane_helper_funcs"></a>1.2.2 struct drm_plane_helper_funcs</h5><p> struct drm_plane_helper_funcs定义了一些常用的plane助手操作函数，定义在include&#x2F;drm&#x2F;drm_modeset_helper_vtables.h；</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br><span class="line">88</span><br><span class="line">89</span><br><span class="line">90</span><br><span class="line">91</span><br><span class="line">92</span><br><span class="line">93</span><br><span class="line">94</span><br><span class="line">95</span><br><span class="line">96</span><br><span class="line">97</span><br><span class="line">98</span><br><span class="line">99</span><br><span class="line">100</span><br><span class="line">101</span><br><span class="line">102</span><br><span class="line">103</span><br><span class="line">104</span><br><span class="line">105</span><br><span class="line">106</span><br><span class="line">107</span><br><span class="line">108</span><br><span class="line">109</span><br><span class="line">110</span><br><span class="line">111</span><br><span class="line">112</span><br><span class="line">113</span><br><span class="line">114</span><br><span class="line">115</span><br><span class="line">116</span><br><span class="line">117</span><br><span class="line">118</span><br><span class="line">119</span><br><span class="line">120</span><br><span class="line">121</span><br><span class="line">122</span><br><span class="line">123</span><br><span class="line">124</span><br><span class="line">125</span><br><span class="line">126</span><br><span class="line">127</span><br><span class="line">128</span><br><span class="line">129</span><br><span class="line">130</span><br><span class="line">131</span><br><span class="line">132</span><br><span class="line">133</span><br><span class="line">134</span><br><span class="line">135</span><br><span class="line">136</span><br><span class="line">137</span><br><span class="line">138</span><br><span class="line">139</span><br><span class="line">140</span><br><span class="line">141</span><br><span class="line">142</span><br><span class="line">143</span><br><span class="line">144</span><br><span class="line">145</span><br><span class="line">146</span><br><span class="line">147</span><br><span class="line">148</span><br><span class="line">149</span><br><span class="line">150</span><br><span class="line">151</span><br><span class="line">152</span><br><span class="line">153</span><br><span class="line">154</span><br><span class="line">155</span><br><span class="line">156</span><br><span class="line">157</span><br><span class="line">158</span><br><span class="line">159</span><br><span class="line">160</span><br><span class="line">161</span><br><span class="line">162</span><br><span class="line">163</span><br><span class="line">164</span><br><span class="line">165</span><br><span class="line">166</span><br><span class="line">167</span><br><span class="line">168</span><br><span class="line">169</span><br><span class="line">170</span><br><span class="line">171</span><br><span class="line">172</span><br><span class="line">173</span><br><span class="line">174</span><br><span class="line">175</span><br><span class="line">176</span><br><span class="line">177</span><br><span class="line">178</span><br><span class="line">179</span><br><span class="line">180</span><br><span class="line">181</span><br><span class="line">182</span><br><span class="line">183</span><br><span class="line">184</span><br><span class="line">185</span><br><span class="line">186</span><br><span class="line">187</span><br><span class="line">188</span><br><span class="line">189</span><br><span class="line">190</span><br><span class="line">191</span><br><span class="line">192</span><br><span class="line">193</span><br><span class="line">194</span><br><span class="line">195</span><br><span class="line">196</span><br><span class="line">197</span><br><span class="line">198</span><br><span class="line">199</span><br><span class="line">200</span><br><span class="line">201</span><br><span class="line">202</span><br><span class="line">203</span><br><span class="line">204</span><br><span class="line">205</span><br><span class="line">206</span><br><span class="line">207</span><br><span class="line">208</span><br><span class="line">209</span><br><span class="line">210</span><br><span class="line">211</span><br><span class="line">212</span><br><span class="line">213</span><br><span class="line">214</span><br><span class="line">215</span><br><span class="line">216</span><br><span class="line">217</span><br><span class="line">218</span><br><span class="line">219</span><br><span class="line">220</span><br><span class="line">221</span><br><span class="line">222</span><br><span class="line">223</span><br><span class="line">224</span><br><span class="line">225</span><br><span class="line">226</span><br><span class="line">227</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * struct drm_plane_helper_funcs - helper operations for planes</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * These functions are used by the atomic helpers and by the transitional plane</span></span><br><span class="line"><span class="comment"> * helpers.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="class"><span class="keyword">struct</span> <span class="title">drm_plane_helper_funcs</span> &#123;</span></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @prepare_fb:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This hook is to prepare a framebuffer for scanout by e.g. pinning</span></span><br><span class="line"><span class="comment">         * its backing storage or relocating it into a contiguous block of</span></span><br><span class="line"><span class="comment">         * VRAM. Other possible preparatory work includes flushing caches.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This function must not block for outstanding rendering, since it is</span></span><br><span class="line"><span class="comment">         * called in the context of the atomic IOCTL even for async commits to</span></span><br><span class="line"><span class="comment">         * be able to return any errors to userspace. Instead the recommended</span></span><br><span class="line"><span class="comment">         * way is to fill out the &amp;drm_plane_state.fence of the passed-in</span></span><br><span class="line"><span class="comment">         * &amp;drm_plane_state. If the driver doesn&#x27;t support native fences then</span></span><br><span class="line"><span class="comment">         * equivalent functionality should be implemented through private</span></span><br><span class="line"><span class="comment">         * members in the plane structure.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * For GEM drivers who neither have a @prepare_fb nor @cleanup_fb hook</span></span><br><span class="line"><span class="comment">         * set drm_gem_plane_helper_prepare_fb() is called automatically to</span></span><br><span class="line"><span class="comment">         * implement this. Other drivers which need additional plane processing</span></span><br><span class="line"><span class="comment">         * can call drm_gem_plane_helper_prepare_fb() from their @prepare_fb</span></span><br><span class="line"><span class="comment">         * hook.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * The resources acquired in @prepare_fb persist after the end of</span></span><br><span class="line"><span class="comment">         * the atomic commit. Resources that can be release at the commit&#x27;s end</span></span><br><span class="line"><span class="comment">         * should be acquired in @begin_fb_access and released in @end_fb_access.</span></span><br><span class="line"><span class="comment">         * For example, a GEM buffer&#x27;s pin operation belongs into @prepare_fb to</span></span><br><span class="line"><span class="comment">         * keep the buffer pinned after the commit. But a vmap operation for</span></span><br><span class="line"><span class="comment">         * shadow-plane helpers belongs into @begin_fb_access, so that atomic</span></span><br><span class="line"><span class="comment">         * helpers remove the mapping at the end of the commit.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * The helpers will call @cleanup_fb with matching arguments for every</span></span><br><span class="line"><span class="comment">         * successful call to this hook.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is used by the atomic modeset helpers and by the</span></span><br><span class="line"><span class="comment">         * transitional plane helpers, but it is optional. See @begin_fb_access</span></span><br><span class="line"><span class="comment">         * for preparing per-commit resources.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success or one of the following negative error codes allowed by</span></span><br><span class="line"><span class="comment">         * the &amp;drm_mode_config_funcs.atomic_commit vfunc. When using helpers</span></span><br><span class="line"><span class="comment">         * this callback is the only one which can fail an atomic commit,</span></span><br><span class="line"><span class="comment">         * everything else must complete successfully.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*prepare_fb)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                          <span class="keyword">struct</span> drm_plane_state *new_state);</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @cleanup_fb:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This hook is called to clean up any resources allocated for the given</span></span><br><span class="line"><span class="comment">         * framebuffer and plane configuration in @prepare_fb.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is used by the atomic modeset helpers and by the</span></span><br><span class="line"><span class="comment">         * transitional plane helpers, but it is optional.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*cleanup_fb)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                           <span class="keyword">struct</span> drm_plane_state *old_state);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @begin_fb_access:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This hook prepares the plane for access during an atomic commit.</span></span><br><span class="line"><span class="comment">         * In contrast to @prepare_fb, resources acquired in @begin_fb_access,</span></span><br><span class="line"><span class="comment">         * are released at the end of the atomic commit in @end_fb_access.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * For example, with shadow-plane helpers, the GEM buffer&#x27;s vmap</span></span><br><span class="line"><span class="comment">         * operation belongs into @begin_fb_access, so that the buffer&#x27;s</span></span><br><span class="line"><span class="comment">         * memory will be unmapped at the end of the commit in @end_fb_access.</span></span><br><span class="line"><span class="comment">         * But a GEM buffer&#x27;s pin operation belongs into @prepare_fb</span></span><br><span class="line"><span class="comment">         * to keep the buffer pinned after the commit.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * The callback is used by the atomic modeset helpers, but it is optional.</span></span><br><span class="line"><span class="comment">         * See @end_fb_cleanup for undoing the effects of @begin_fb_access and</span></span><br><span class="line"><span class="comment">         * @prepare_fb for acquiring resources until the next pageflip.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Returns:</span></span><br><span class="line"><span class="comment">         * 0 on success, or a negative errno code otherwise.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*begin_fb_access)(<span class="keyword">struct</span> drm_plane *plane, <span class="keyword">struct</span> drm_plane_state *new_plane_state);</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @end_fb_access:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This hook cleans up resources allocated by @begin_fb_access. It it called</span></span><br><span class="line"><span class="comment">         * at the end of a commit for the new plane state.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*end_fb_access)(<span class="keyword">struct</span> drm_plane *plane, <span class="keyword">struct</span> drm_plane_state *new_plane_state);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_check:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers should check plane specific constraints in this hook.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * When using drm_atomic_helper_check_planes() plane&#x27;s @atomic_check</span></span><br><span class="line"><span class="comment">         * hooks are called before the ones for CRTCs, which allows drivers to</span></span><br><span class="line"><span class="comment">         * request shared resources that the CRTC controls here. For more</span></span><br><span class="line"><span class="comment">         * complicated dependencies the driver can call the provided check helpers</span></span><br><span class="line"><span class="comment">         * multiple times until the computed state has a final configuration and</span></span><br><span class="line"><span class="comment">         * everything has been checked.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This function is also allowed to inspect any other object&#x27;s state and</span></span><br><span class="line"><span class="comment">         * can add more state objects to the atomic commit if needed. Care must</span></span><br><span class="line"><span class="comment">         * be taken though to ensure that state check and compute functions for</span></span><br><span class="line"><span class="comment">         * these added states are all called, and derived state in other objects</span></span><br><span class="line"><span class="comment">         * all updated. Again the recommendation is to just call check helpers</span></span><br><span class="line"><span class="comment">         * until a maximal configuration is reached.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is used by the atomic modeset helpers and by the</span></span><br><span class="line"><span class="comment">         * transitional plane helpers, but it is optional.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * <span class="doctag">NOTE:</span></span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This function is called in the check phase of an atomic update. The</span></span><br><span class="line"><span class="comment">         * driver is not allowed to change anything outside of the</span></span><br><span class="line"><span class="comment">         * &amp;drm_atomic_state update tracking structure.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * 0 on success, -EINVAL if the state or the transition can&#x27;t be</span></span><br><span class="line"><span class="comment">         * supported, -ENOMEM on memory allocation failure and -EDEADLK if an</span></span><br><span class="line"><span class="comment">         * attempt to obtain another state object ran into a &amp;drm_modeset_lock</span></span><br><span class="line"><span class="comment">         * deadlock.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*<span class="type">atomic_check</span>)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                            <span class="keyword">struct</span> drm_atomic_state *state);</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_update:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers should use this function to update the plane state.  This</span></span><br><span class="line"><span class="comment">         * hook is called in-between the &amp;drm_crtc_helper_funcs.atomic_begin and</span></span><br><span class="line"><span class="comment">         * drm_crtc_helper_funcs.atomic_flush callbacks.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Note that the power state of the display pipe when this function is</span></span><br><span class="line"><span class="comment">         * called depends upon the exact helpers and calling sequence the driver</span></span><br><span class="line"><span class="comment">         * has picked. See drm_atomic_helper_commit_planes() for a discussion of</span></span><br><span class="line"><span class="comment">         * the tradeoffs and variants of plane commit helpers.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is used by the atomic modeset helpers and by the</span></span><br><span class="line"><span class="comment">         * transitional plane helpers, but it is optional.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*<span class="type">atomic_update</span>)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                              <span class="keyword">struct</span> drm_atomic_state *state);</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_disable:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers should use this function to unconditionally disable a plane.</span></span><br><span class="line"><span class="comment">         * This hook is called in-between the</span></span><br><span class="line"><span class="comment">         * &amp;drm_crtc_helper_funcs.atomic_begin and</span></span><br><span class="line"><span class="comment">         * drm_crtc_helper_funcs.atomic_flush callbacks. It is an alternative to</span></span><br><span class="line"><span class="comment">         * @atomic_update, which will be called for disabling planes, too, if</span></span><br><span class="line"><span class="comment">         * the @atomic_disable hook isn&#x27;t implemented.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This hook is also useful to disable planes in preparation of a modeset,</span></span><br><span class="line"><span class="comment">         * by calling drm_atomic_helper_disable_planes_on_crtc() from the</span></span><br><span class="line"><span class="comment">         * &amp;drm_crtc_helper_funcs.disable hook.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Note that the power state of the display pipe when this function is</span></span><br><span class="line"><span class="comment">         * called depends upon the exact helpers and calling sequence the driver</span></span><br><span class="line"><span class="comment">         * has picked. See drm_atomic_helper_commit_planes() for a discussion of</span></span><br><span class="line"><span class="comment">         * the tradeoffs and variants of plane commit helpers.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This callback is used by the atomic modeset helpers and by the</span></span><br><span class="line"><span class="comment">         * transitional plane helpers, but it is optional.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*atomic_disable)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                               <span class="keyword">struct</span> drm_atomic_state *state);</span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_async_check:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers should set this function pointer to check if the plane&#x27;s</span></span><br><span class="line"><span class="comment">         * atomic state can be updated in a async fashion. Here async means</span></span><br><span class="line"><span class="comment">         * &quot;not vblank synchronized&quot;.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This hook is called by drm_atomic_async_check() to establish if a</span></span><br><span class="line"><span class="comment">         * given update can be committed asynchronously, that is, if it can</span></span><br><span class="line"><span class="comment">         * jump ahead of the state currently queued for update.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * RETURNS:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Return 0 on success and any error returned indicates that the update</span></span><br><span class="line"><span class="comment">         * can not be applied in asynchronous manner.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">int</span> (*atomic_async_check)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                                  <span class="keyword">struct</span> drm_atomic_state *state);</span><br><span class="line"></span><br><span class="line">        <span class="comment">/**</span></span><br><span class="line"><span class="comment">         * @atomic_async_update:</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers should set this function pointer to perform asynchronous</span></span><br><span class="line"><span class="comment">         * updates of planes, that is, jump ahead of the currently queued</span></span><br><span class="line"><span class="comment">         * state and update the plane. Here async means &quot;not vblank</span></span><br><span class="line"><span class="comment">         * synchronized&quot;.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * This hook is called by drm_atomic_helper_async_commit().</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * An async update will happen on legacy cursor updates. An async</span></span><br><span class="line"><span class="comment">         * update won&#x27;t happen if there is an outstanding commit modifying</span></span><br><span class="line"><span class="comment">         * the same plane.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * When doing async_update drivers shouldn&#x27;t replace the</span></span><br><span class="line"><span class="comment">         * &amp;drm_plane_state but update the current one with the new plane</span></span><br><span class="line"><span class="comment">         * configurations in the new plane_state.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * Drivers should also swap the framebuffers between current plane</span></span><br><span class="line"><span class="comment">         * state (&amp;drm_plane.state) and new_state.</span></span><br><span class="line"><span class="comment">         * This is required since cleanup for async commits is performed on</span></span><br><span class="line"><span class="comment">         * the new state, rather than old state like for traditional commits.</span></span><br><span class="line"><span class="comment">         * Since we want to give up the reference on the current (old) fb</span></span><br><span class="line"><span class="comment">         * instead of our brand new one, swap them in the driver during the</span></span><br><span class="line"><span class="comment">         * async commit.</span></span><br><span class="line"><span class="comment">         *</span></span><br><span class="line"><span class="comment">         * <span class="doctag">FIXME:</span></span></span><br><span class="line"><span class="comment">         *  - It only works for single plane updates</span></span><br><span class="line"><span class="comment">         *  - Async Pageflips are not supported yet</span></span><br><span class="line"><span class="comment">         *  - Some hw might still scan out the old buffer until the next</span></span><br><span class="line"><span class="comment">         *    vblank, however we let go of the fb references as soon as</span></span><br><span class="line"><span class="comment">         *    we run this hook. For now drivers must implement their own workers</span></span><br><span class="line"><span class="comment">         *    for deferring if needed, until a common solution is created.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="type">void</span> (*atomic_async_update)(<span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                                    <span class="keyword">struct</span> drm_atomic_state *state);</span><br><span class="line">&#125;;</span><br></pre></td></tr></table></figure>

<p>这里定义了一大堆回调函数：</p>
<ul>
<li>prepare_fb：准备fb，主要包括设置fb fence,  映射fb虚拟地址等；</li>
<li>cleanup_fb：清除在prepare_fb分配的给framebuffer和plane的资源；</li>
<li>begin_fb_access：</li>
<li>end_fb_access：</li>
<li>atomic_check：检查该挂钩中的plane特定约束；</li>
<li>atomic_update：更新plane状态；</li>
<li>atomic_disable：关闭；</li>
<li>atomic_async_check：异步检查；</li>
<li>atomic_async_update：异步更新状态；</li>
</ul>
<h3 id="二、plane-API"><a href="#二、plane-API" class="headerlink" title="二、plane API"></a>二、plane API</h3><h4 id="2-1-drm-universal-plane-init"><a href="#2-1-drm-universal-plane-init" class="headerlink" title="2.1 drm_universal_plane_init"></a>2.1 drm_universal_plane_init</h4><p>drm_universal_plane_init函数用于初始化一个通用的plane对象，定义在drivers&#x2F;gpu&#x2F;drm&#x2F;drm_plane.c：</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * drm_universal_plane_init - Initialize a new universal plane object</span></span><br><span class="line"><span class="comment"> * @dev: DRM device</span></span><br><span class="line"><span class="comment"> * @plane: plane object to init</span></span><br><span class="line"><span class="comment"> * @possible_crtcs: bitmask of possible CRTCs</span></span><br><span class="line"><span class="comment"> * @funcs: callbacks for the new plane</span></span><br><span class="line"><span class="comment"> * @formats: array of supported formats (DRM_FORMAT\_\*)</span></span><br><span class="line"><span class="comment"> * @format_count: number of elements in @formats</span></span><br><span class="line"><span class="comment"> * @format_modifiers: array of struct drm_format modifiers terminated by</span></span><br><span class="line"><span class="comment"> *                    DRM_FORMAT_MOD_INVALID</span></span><br><span class="line"><span class="comment"> * @type: type of plane (overlay, primary, cursor)</span></span><br><span class="line"><span class="comment"> * @name: printf style format string for the plane name, or NULL for default name</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Initializes a plane object of type @type. The &amp;drm_plane_funcs.destroy hook</span></span><br><span class="line"><span class="comment"> * should call drm_plane_cleanup() and kfree() the plane structure. The plane</span></span><br><span class="line"><span class="comment"> * structure should not be allocated with devm_kzalloc().</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Note: consider using drmm_universal_plane_alloc() instead of</span></span><br><span class="line"><span class="comment"> * drm_universal_plane_init() to let the DRM managed resource infrastructure</span></span><br><span class="line"><span class="comment"> * take care of cleanup and deallocation.</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Drivers that only support the DRM_FORMAT_MOD_LINEAR modifier support may set</span></span><br><span class="line"><span class="comment"> * @format_modifiers to NULL. The plane will advertise the linear modifier.</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Returns:</span></span><br><span class="line"><span class="comment"> * Zero on success, error code on failure.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="type">int</span> <span class="title function_">drm_universal_plane_init</span><span class="params">(<span class="keyword">struct</span> drm_device *dev, <span class="keyword">struct</span> drm_plane *plane,</span></span><br><span class="line"><span class="params">                             <span class="type">uint32_t</span> possible_crtcs,</span></span><br><span class="line"><span class="params">                             <span class="type">const</span> <span class="keyword">struct</span> drm_plane_funcs *funcs,</span></span><br><span class="line"><span class="params">                             <span class="type">const</span> <span class="type">uint32_t</span> *formats, <span class="type">unsigned</span> <span class="type">int</span> format_count,</span></span><br><span class="line"><span class="params">                             <span class="type">const</span> <span class="type">uint64_t</span> *format_modifiers,</span></span><br><span class="line"><span class="params">                             <span class="keyword">enum</span> drm_plane_type type,</span></span><br><span class="line"><span class="params">                             <span class="type">const</span> <span class="type">char</span> *name, ...)</span></span><br><span class="line">&#123;</span><br><span class="line">        va_list ap;</span><br><span class="line">        <span class="type">int</span> ret;</span><br><span class="line"></span><br><span class="line">        WARN_ON(!funcs-&gt;destroy);</span><br><span class="line"></span><br><span class="line">        va_start(ap, name);</span><br><span class="line">        ret = __drm_universal_plane_init(dev, plane, possible_crtcs, funcs,</span><br><span class="line">                                         formats, format_count, format_modifiers,</span><br><span class="line">                                         type, name, ap);</span><br><span class="line">        va_end(ap);</span><br><span class="line">        <span class="keyword">return</span> ret;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p>函数接收以下参数：</p>
<ul>
<li>dev：drm设备；</li>
<li>plane：要初始化的plane对象；</li>
<li>possible_crtcs：可能的CRTCs的位掩码；</li>
<li>funcs：plane的控制函数集合；</li>
<li>formats：支持的格式数组（DRM_FORMAT_*）；</li>
<li>format_count：formats数组的长度；</li>
<li>format_modifiers：以DRM_FORMAT_MOD_INVALID结尾的drm_format modifiers结构体数组；</li>
<li>type：plane的类型；</li>
<li>name：plane名字的格式化字符串，如果为NULL则使用默认名称；</li>
</ul>
<p>具体实现位于函数__drm_universal_plane_init：</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br><span class="line">88</span><br><span class="line">89</span><br><span class="line">90</span><br><span class="line">91</span><br><span class="line">92</span><br><span class="line">93</span><br><span class="line">94</span><br><span class="line">95</span><br><span class="line">96</span><br><span class="line">97</span><br><span class="line">98</span><br><span class="line">99</span><br><span class="line">100</span><br><span class="line">101</span><br><span class="line">102</span><br><span class="line">103</span><br><span class="line">104</span><br><span class="line">105</span><br><span class="line">106</span><br><span class="line">107</span><br><span class="line">108</span><br><span class="line">109</span><br><span class="line">110</span><br><span class="line">111</span><br><span class="line">112</span><br><span class="line">113</span><br><span class="line">114</span><br><span class="line">115</span><br><span class="line">116</span><br><span class="line">117</span><br><span class="line">118</span><br><span class="line">119</span><br><span class="line">120</span><br><span class="line">121</span><br><span class="line">122</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">static</span> <span class="type">int</span> __drm_universal_plane_init(<span class="keyword">struct</span> drm_device *dev,</span><br><span class="line">                                      <span class="keyword">struct</span> drm_plane *plane,</span><br><span class="line">                                      <span class="type">uint32_t</span> possible_crtcs,</span><br><span class="line">                                      <span class="type">const</span> <span class="keyword">struct</span> drm_plane_funcs *funcs,</span><br><span class="line">                                      <span class="type">const</span> <span class="type">uint32_t</span> *formats,</span><br><span class="line">                                      <span class="type">unsigned</span> <span class="type">int</span> format_count,</span><br><span class="line">                                      <span class="type">const</span> <span class="type">uint64_t</span> *format_modifiers,</span><br><span class="line">                                      <span class="keyword">enum</span> drm_plane_type type,</span><br><span class="line">                                      <span class="type">const</span> <span class="type">char</span> *name, va_list ap)</span><br><span class="line">&#123;</span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_mode_config</span> *<span class="title">config</span> =</span> &amp;dev-&gt;mode_config;  <span class="comment">// 获取显示模式配置</span></span><br><span class="line">        <span class="type">static</span> <span class="type">const</span> <span class="type">uint64_t</span> default_modifiers[] = &#123;</span><br><span class="line">                DRM_FORMAT_MOD_LINEAR,</span><br><span class="line">        &#125;;</span><br><span class="line">        <span class="type">unsigned</span> <span class="type">int</span> format_modifier_count = <span class="number">0</span>;</span><br><span class="line">        <span class="type">int</span> ret;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/* plane index is used with 32bit bitmasks */</span></span><br><span class="line">        <span class="keyword">if</span> (WARN_ON(config-&gt;num_total_plane &gt;= <span class="number">32</span>))</span><br><span class="line">                <span class="keyword">return</span> -EINVAL;</span><br><span class="line"></span><br><span class="line">        <span class="comment">/*</span></span><br><span class="line"><span class="comment">         * First driver to need more than 64 formats needs to fix this. Each</span></span><br><span class="line"><span class="comment">         * format is encoded as a bit and the current code only supports a u64.</span></span><br><span class="line"><span class="comment">         */</span></span><br><span class="line">        <span class="keyword">if</span> (WARN_ON(format_count &gt; <span class="number">64</span>))</span><br><span class="line">                <span class="keyword">return</span> -EINVAL;</span><br><span class="line"></span><br><span class="line">        WARN_ON(drm_drv_uses_atomic_modeset(dev) &amp;&amp;</span><br><span class="line">                (!funcs-&gt;atomic_destroy_state ||</span><br><span class="line">                 !funcs-&gt;atomic_duplicate_state));</span><br><span class="line"></span><br><span class="line">        ret = drm_mode_object_add(dev, &amp;plane-&gt;base, DRM_MODE_OBJECT_PLANE); <span class="comment">// 初始化drm_mode_object成员id、type</span></span><br><span class="line">        <span class="keyword">if</span> (ret)</span><br><span class="line">                <span class="keyword">return</span> ret;</span><br><span class="line"></span><br><span class="line">        drm_modeset_lock_init(&amp;plane-&gt;mutex); <span class="comment">// 初始化互斥锁</span></span><br><span class="line"></span><br><span class="line">        plane-&gt;base.properties = &amp;plane-&gt;properties;</span><br><span class="line">        plane-&gt;dev = dev;</span><br><span class="line">        plane-&gt;funcs = funcs;</span><br><span class="line">        plane-&gt;format_types = kmalloc_array(format_count, <span class="keyword">sizeof</span>(<span class="type">uint32_t</span>),</span><br><span class="line">                                            GFP_KERNEL);</span><br><span class="line">        <span class="keyword">if</span> (!plane-&gt;format_types) &#123;</span><br><span class="line">                DRM_DEBUG_KMS(<span class="string">&quot;out of memory when allocating plane\n&quot;</span>);</span><br><span class="line">                drm_mode_object_unregister(dev, &amp;plane-&gt;base);</span><br><span class="line">                <span class="keyword">return</span> -ENOMEM;</span><br><span class="line">        &#125;</span><br><span class="line"></span><br><span class="line">        <span class="keyword">if</span> (format_modifiers) &#123;</span><br><span class="line">                <span class="type">const</span> <span class="type">uint64_t</span> *temp_modifiers = format_modifiers;</span><br><span class="line"></span><br><span class="line">                <span class="keyword">while</span> (*temp_modifiers++ != DRM_FORMAT_MOD_INVALID)</span><br><span class="line">                        format_modifier_count++;</span><br><span class="line">        &#125; <span class="keyword">else</span> &#123;</span><br><span class="line">                <span class="keyword">if</span> (!dev-&gt;mode_config.fb_modifiers_not_supported) &#123;</span><br><span class="line">                        format_modifiers = default_modifiers;</span><br><span class="line">                        format_modifier_count = ARRAY_SIZE(default_modifiers);</span><br><span class="line">                &#125;</span><br><span class="line">        &#125;</span><br><span class="line">        <span class="comment">/* autoset the cap and check for consistency across all planes */</span></span><br><span class="line">        drm_WARN_ON(dev, config-&gt;fb_modifiers_not_supported &amp;&amp;</span><br><span class="line">                                format_modifier_count);</span><br><span class="line"></span><br><span class="line">        plane-&gt;modifier_count = format_modifier_count;</span><br><span class="line">        plane-&gt;modifiers = kmalloc_array(format_modifier_count,</span><br><span class="line">                                         <span class="keyword">sizeof</span>(format_modifiers[<span class="number">0</span>]),</span><br><span class="line">                                         GFP_KERNEL);</span><br><span class="line"></span><br><span class="line">        <span class="keyword">if</span> (format_modifier_count &amp;&amp; !plane-&gt;modifiers) &#123;</span><br><span class="line">                DRM_DEBUG_KMS(<span class="string">&quot;out of memory when allocating plane\n&quot;</span>);</span><br><span class="line">                kfree(plane-&gt;format_types);</span><br><span class="line">                drm_mode_object_unregister(dev, &amp;plane-&gt;base);</span><br><span class="line">                <span class="keyword">return</span> -ENOMEM;</span><br><span class="line">        &#125;</span><br><span class="line"></span><br><span class="line">        <span class="keyword">if</span> (name) &#123;</span><br><span class="line">                plane-&gt;name = kvasprintf(GFP_KERNEL, name, ap);</span><br><span class="line">        &#125; <span class="keyword">else</span> &#123;</span><br><span class="line">                plane-&gt;name = kasprintf(GFP_KERNEL, <span class="string">&quot;plane-%d&quot;</span>,</span><br><span class="line">                                        drm_num_planes(dev));</span><br><span class="line">        &#125;</span><br><span class="line">        <span class="keyword">if</span> (!plane-&gt;name) &#123;</span><br><span class="line">                kfree(plane-&gt;format_types);</span><br><span class="line">                kfree(plane-&gt;modifiers);</span><br><span class="line">                drm_mode_object_unregister(dev, &amp;plane-&gt;base);</span><br><span class="line">                <span class="keyword">return</span> -ENOMEM;</span><br><span class="line">        &#125;</span><br><span class="line"></span><br><span class="line">        <span class="built_in">memcpy</span>(plane-&gt;format_types, formats, format_count * <span class="keyword">sizeof</span>(<span class="type">uint32_t</span>));</span><br><span class="line">        plane-&gt;format_count = format_count;</span><br><span class="line">        <span class="built_in">memcpy</span>(plane-&gt;modifiers, format_modifiers,</span><br><span class="line">               format_modifier_count * <span class="keyword">sizeof</span>(format_modifiers[<span class="number">0</span>]));</span><br><span class="line">        plane-&gt;possible_crtcs = possible_crtcs;</span><br><span class="line">        plane-&gt;type = type;</span><br><span class="line"></span><br><span class="line">        list_add_tail(&amp;plane-&gt;head, &amp;config-&gt;plane_list);</span><br><span class="line">        plane-&gt;index = config-&gt;num_total_plane++;</span><br><span class="line"></span><br><span class="line">        drm_object_attach_property(&amp;plane-&gt;base,</span><br><span class="line">                                   config-&gt;plane_type_property, <span class="comment">// 附加属性到plane-&gt;base</span></span><br><span class="line">                                   plane-&gt;type);</span><br><span class="line"></span><br><span class="line">        <span class="keyword">if</span> (drm_core_check_feature(dev, DRIVER_ATOMIC)) &#123;</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_fb_id, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_in_fence_fd, <span class="number">-1</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_crtc_id, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_crtc_x, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_crtc_y, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_crtc_w, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_crtc_h, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_src_x, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_src_y, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_src_w, <span class="number">0</span>);</span><br><span class="line">                drm_object_attach_property(&amp;plane-&gt;base, config-&gt;prop_src_h, <span class="number">0</span>);</span><br><span class="line">        &#125;</span><br><span class="line"></span><br><span class="line">        <span class="keyword">if</span> (format_modifier_count)</span><br><span class="line">                create_in_format_blob(dev, plane);</span><br><span class="line"></span><br><span class="line">        <span class="keyword">return</span> <span class="number">0</span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<h4 id="2-2-drm-mode-object-add"><a href="#2-2-drm-mode-object-add" class="headerlink" title="2.2 drm_mode_object_add"></a>2.2 drm_mode_object_add</h4><p>drm_mode_object_add基于基数树为drm_mode_object分配一个唯一Id，定义在drivers&#x2F;gpu&#x2F;drm&#x2F;drm_mode_object.c：</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> * Internal function to assign a slot in the object idr and optionally</span></span><br><span class="line"><span class="comment"> * register the object into the idr.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="type">int</span> __drm_mode_object_add(<span class="keyword">struct</span> drm_device *dev, <span class="keyword">struct</span> drm_mode_object *obj,</span><br><span class="line">                          <span class="type">uint32_t</span> obj_type, <span class="type">bool</span> register_obj,</span><br><span class="line">                          <span class="type">void</span> (*obj_free_cb)(<span class="keyword">struct</span> kref *kref))</span><br><span class="line">&#123;</span><br><span class="line">        <span class="type">int</span> ret;</span><br><span class="line"></span><br><span class="line">        WARN_ON(!dev-&gt;driver-&gt;load &amp;&amp; dev-&gt;registered &amp;&amp; !obj_free_cb);</span><br><span class="line"></span><br><span class="line">        mutex_lock(&amp;dev-&gt;mode_config.idr_mutex);  <span class="comment">// 获取互斥锁</span></span><br><span class="line">        ret = idr_alloc(&amp;dev-&gt;mode_config.object_idr, register_obj ? obj : <span class="literal">NULL</span>,</span><br><span class="line">                        <span class="number">1</span>, <span class="number">0</span>, GFP_KERNEL); <span class="comment">// 这里分配一个唯一id，基于idr（redix树）</span></span><br><span class="line">        <span class="keyword">if</span> (ret &gt;= <span class="number">0</span>) &#123;</span><br><span class="line">                <span class="comment">/*</span></span><br><span class="line"><span class="comment">                 * Set up the object linking under the protection of the idr</span></span><br><span class="line"><span class="comment">                 * lock so that other users can&#x27;t see inconsistent state.</span></span><br><span class="line"><span class="comment">                 */</span></span><br><span class="line">                obj-&gt;id = ret;         <span class="comment">// 设置唯一标识符</span></span><br><span class="line">                obj-&gt;type = obj_type;  <span class="comment">// 设置对象的类型</span></span><br><span class="line">                <span class="keyword">if</span> (obj_free_cb) &#123;</span><br><span class="line">                        obj-&gt;free_cb = obj_free_cb;</span><br><span class="line">                        kref_init(&amp;obj-&gt;refcount);   <span class="comment">// 初始化引用计数</span></span><br><span class="line">                &#125;</span><br><span class="line">        &#125;</span><br><span class="line">        mutex_unlock(&amp;dev-&gt;mode_config.idr_mutex); <span class="comment">// 释放互斥锁</span></span><br><span class="line"></span><br><span class="line">        <span class="keyword">return</span> ret &lt; <span class="number">0</span> ? ret : <span class="number">0</span>;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * drm_mode_object_add - allocate a new modeset identifier</span></span><br><span class="line"><span class="comment"> * @dev: DRM device</span></span><br><span class="line"><span class="comment"> * @obj: object pointer, used to generate unique ID</span></span><br><span class="line"><span class="comment"> * @obj_type: object type</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Create a unique identifier based on @ptr in @dev&#x27;s identifier space.  Used</span></span><br><span class="line"><span class="comment"> * for tracking modes, CRTCs and connectors.</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Returns:</span></span><br><span class="line"><span class="comment"> * Zero on success, error code on failure.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="type">int</span> <span class="title function_">drm_mode_object_add</span><span class="params">(<span class="keyword">struct</span> drm_device *dev,</span></span><br><span class="line"><span class="params">                        <span class="keyword">struct</span> drm_mode_object *obj, <span class="type">uint32_t</span> obj_type)</span></span><br><span class="line">&#123;</span><br><span class="line">        <span class="keyword">return</span> __drm_mode_object_add(dev, obj, obj_type, <span class="literal">true</span>, <span class="literal">NULL</span>);</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<h4 id="2-3-drm-object-attach-property"><a href="#2-3-drm-object-attach-property" class="headerlink" title="2.3 drm_object_attach_property"></a>2.3 drm_object_attach_property</h4><p>drm_object_attach_property用于附加属性到drm_mode_object，定义在drivers&#x2F;gpu&#x2F;drm&#x2F;drm_mode_object.c：</p>
<figure class="highlight c"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * drm_object_attach_property - attach a property to a modeset object</span></span><br><span class="line"><span class="comment"> * @obj: drm modeset object</span></span><br><span class="line"><span class="comment"> * @property: property to attach</span></span><br><span class="line"><span class="comment"> * @init_val: initial value of the property</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * This attaches the given property to the modeset object with the given initial</span></span><br><span class="line"><span class="comment"> * value. Currently this function cannot fail since the properties are stored in</span></span><br><span class="line"><span class="comment"> * a statically sized array.</span></span><br><span class="line"><span class="comment"> *</span></span><br><span class="line"><span class="comment"> * Note that all properties must be attached before the object itself is</span></span><br><span class="line"><span class="comment"> * registered and accessible from userspace.</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="type">void</span> <span class="title function_">drm_object_attach_property</span><span class="params">(<span class="keyword">struct</span> drm_mode_object *obj,   <span class="comment">// 需要附加属性的modeset object</span></span></span><br><span class="line"><span class="params">                                <span class="keyword">struct</span> drm_property *property, <span class="comment">// 需要附加的属性</span></span></span><br><span class="line"><span class="params">                                <span class="type">uint64_t</span> init_val)</span> <span class="comment">// 属性值</span></span><br><span class="line">&#123;</span><br><span class="line">        <span class="type">int</span> count = obj-&gt;properties-&gt;count;  <span class="comment">// 获取属性个数</span></span><br><span class="line">        <span class="class"><span class="keyword">struct</span> <span class="title">drm_device</span> *<span class="title">dev</span> =</span> property-&gt;dev; <span class="comment">// 获取drm设备</span></span><br><span class="line"></span><br><span class="line"></span><br><span class="line">        <span class="keyword">if</span> (obj-&gt;type == DRM_MODE_OBJECT_CONNECTOR) &#123;  <span class="comment">// 如果是connector类型</span></span><br><span class="line">                <span class="class"><span class="keyword">struct</span> <span class="title">drm_connector</span> *<span class="title">connector</span> =</span> obj_to_connector(obj);</span><br><span class="line"></span><br><span class="line">                WARN_ON(!dev-&gt;driver-&gt;load &amp;&amp;</span><br><span class="line">                        connector-&gt;registration_state == DRM_CONNECTOR_REGISTERED);</span><br><span class="line">        &#125; <span class="keyword">else</span> &#123;</span><br><span class="line">                WARN_ON(!dev-&gt;driver-&gt;load &amp;&amp; dev-&gt;registered);</span><br><span class="line">        &#125;</span><br><span class="line"></span><br><span class="line">        <span class="keyword">if</span> (count == DRM_OBJECT_MAX_PROPERTY) &#123;</span><br><span class="line">                WARN(<span class="number">1</span>, <span class="string">&quot;Failed to attach object property (type: 0x%x). Please &quot;</span></span><br><span class="line">                        <span class="string">&quot;increase DRM_OBJECT_MAX_PROPERTY by 1 for each time &quot;</span></span><br><span class="line">                        <span class="string">&quot;you see this message on the same object type.\n&quot;</span>,</span><br><span class="line">                        obj-&gt;type);</span><br><span class="line">                <span class="keyword">return</span>;</span><br><span class="line">        &#125;</span><br><span class="line"></span><br><span class="line">        obj-&gt;properties-&gt;properties[count] = property; <span class="comment">// 保存对象属性</span></span><br><span class="line">        obj-&gt;properties-&gt;values[count] = init_val; <span class="comment">// 属性值</span></span><br><span class="line">        obj-&gt;properties-&gt;count++;  <span class="comment">// 属性计数+1</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p><strong>参考文章</strong></p>
<p><strong>[1] <a target="_blank" rel="noopener" href="https://blog.csdn.net/qq_41709234/article/details/129472180">DRM驱动概念、组成、框架、源码分析</a></strong></p>
<p><strong>[2] <a target="_blank" rel="noopener" href="https://blog.csdn.net/zichuanning520/article/details/127047436">linux驱动系列学习之DRM（十）</a></strong></p>
<p><strong>[3] <a target="_blank" rel="noopener" href="https://blog.csdn.net/M120674/article/details/123040696">DRM框架（vkms）分析（6）—- plane初始化</a></strong></p>

        
      </div>

         
    </div>
    
     
  </div>
  
    
<nav id="article-nav">
  <a class="article-nav-btn left "
    
      href="/blog/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%E5%AD%90%E7%B3%BB%E7%BB%9F/"
      title=""
     >
    <i class="fa-solid fa-angle-left"></i>
    <p class="title-text">
      
        (No Title)
        
    </p>
  </a>
  <a class="article-nav-btn right "
    
      href="/blog/2023/09/11/rk3399/Rockchip%20RK3399%20-%20DRM%20framebuffer/"
      title=""
     >

    <p class="title-text">
      
        (No Title)
        
    </p>
    <i class="fa-solid fa-angle-right"></i>
  </a>
</nav>


  
</article>

 
    </div>
    <div id="footer-wrapper">
      <footer id="footer">
  
  <div id="footer-info" class="inner">
    
    &copy; 2023 Your Name<br>
    Powered by <a href="https://hexo.io/" target="_blank">Hexo</a> & Theme <a target="_blank" rel="noopener" href="https://github.com/saicaca/hexo-theme-vivia">Vivia</a>
  </div>
</footer>

    </div>
    <div class="back-to-top-wrapper">
    <button id="back-to-top-btn" class="back-to-top-btn hide" onclick="topFunction()">
        <i class="fa-solid fa-angle-up"></i>
    </button>
</div>

<script>
    function topFunction() {
        window.scroll({ top: 0, behavior: 'smooth' });
    }
    let btn = document.getElementById('back-to-top-btn');
    function scrollFunction() {
        if (document.body.scrollTop > 600 || document.documentElement.scrollTop > 600) {
            btn.classList.remove('hide')
        } else {
            btn.classList.add('hide')
        }
    }
    window.onscroll = function() {
        scrollFunction();
    }
</script>

  </div>
  <script src="/blog/js/light-dark-switch.js"></script>
</body>
</html>
